ATLAS-695: Add Titan 1 project to Atlas
Signed-off-by: Jeff Hagelberg <jnhagelberg@us.ibm.com>
This commit is contained in:
parent
46b1b36e97
commit
6fd04d9a8c
|
|
@ -24,31 +24,36 @@
|
|||
<parent>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>apache-atlas</artifactId>
|
||||
<version>0.8-incubating-SNAPSHOT</version>
|
||||
<version>0.8-incubating-SNAPSHOT</version>
|
||||
</parent>
|
||||
<artifactId>atlas-catalog</artifactId>
|
||||
<description>Apache Atlas Business Catalog Module</description>
|
||||
<name>Apache Atlas Business Catalog</name>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<properties>
|
||||
<tinkerpop.version>2.6.0</tinkerpop.version>
|
||||
<titan.version>0.5.4</titan.version>
|
||||
<lucene.version>4.8.1</lucene.version>
|
||||
</properties>
|
||||
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>titan1</id>
|
||||
<activation>
|
||||
<activeByDefault>false</activeByDefault>
|
||||
</activation>
|
||||
<properties>
|
||||
<lucene.version>4.10.4</lucene.version>
|
||||
</properties>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-repository</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-repository</artifactId>
|
||||
<classifier>tests</classifier>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-typesystem</artifactId>
|
||||
|
|
@ -64,11 +69,43 @@
|
|||
<artifactId>atlas-graphdb-api</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- for now, catalog can only be used with Titan 0.5.4 -->
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-titan0</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<!-- for now, keep the titan 0.5.4 / TP 2 dependencies. This will need to be changed to use a
|
||||
more generic query framework that supports both TP2/TP3. Maybe the DSL translation could be changed to use
|
||||
that as well...
|
||||
-->
|
||||
<dependency>
|
||||
<groupId>com.tinkerpop.blueprints</groupId>
|
||||
<artifactId>blueprints-core</artifactId>
|
||||
<version>${tinkerpop.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>com.tinkerpop.gremlin</groupId>
|
||||
<artifactId>gremlin-java</artifactId>
|
||||
<version>${tinkerpop.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-core</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-core</artifactId>
|
||||
<version>${lucene.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-queryparser</artifactId>
|
||||
<version>${lucene.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-analyzers-common</artifactId>
|
||||
<version>${lucene.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
|
|
@ -96,18 +133,6 @@
|
|||
<artifactId>json-simple</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.tinkerpop.blueprints</groupId>
|
||||
<artifactId>blueprints-core</artifactId>
|
||||
<version>${tinkerpop.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.tinkerpop.gremlin</groupId>
|
||||
<artifactId>gremlin-java</artifactId>
|
||||
<version>${tinkerpop.version}</version>
|
||||
</dependency>
|
||||
|
||||
<!-- testing -->
|
||||
<dependency>
|
||||
<groupId>org.easymock</groupId>
|
||||
|
|
|
|||
|
|
@ -30,10 +30,10 @@ import org.apache.atlas.catalog.exception.ResourceNotFoundException;
|
|||
import org.apache.atlas.catalog.projection.Projection;
|
||||
import org.apache.atlas.catalog.projection.ProjectionResult;
|
||||
import org.apache.atlas.repository.Constants;
|
||||
import org.apache.atlas.repository.graphdb.titan0.Titan0GraphDatabase;
|
||||
import org.apache.atlas.repository.graph.AtlasGraphProvider;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.typesystem.persistence.Id;
|
||||
|
||||
import com.thinkaurelius.titan.core.TitanGraph;
|
||||
import com.tinkerpop.blueprints.Compare;
|
||||
import com.tinkerpop.blueprints.Vertex;
|
||||
import com.tinkerpop.gremlin.java.GremlinPipeline;
|
||||
|
|
@ -165,10 +165,9 @@ public abstract class BaseQuery implements AtlasQuery {
|
|||
return request;
|
||||
}
|
||||
|
||||
//todo: abstract
|
||||
// Underlying method is synchronized and caches the graph in a static field
|
||||
protected TitanGraph getGraph() {
|
||||
return Titan0GraphDatabase.getGraphInstance();
|
||||
protected AtlasGraph getGraph() {
|
||||
return AtlasGraphProvider.getGraphInstance();
|
||||
}
|
||||
|
||||
protected VertexWrapper wrapVertex(Vertex v) {
|
||||
|
|
|
|||
|
|
@ -22,10 +22,12 @@ import com.thinkaurelius.titan.core.TitanGraph;
|
|||
import com.tinkerpop.blueprints.Vertex;
|
||||
import com.tinkerpop.gremlin.java.GremlinPipeline;
|
||||
import com.tinkerpop.pipes.Pipe;
|
||||
|
||||
import org.apache.atlas.catalog.Request;
|
||||
import org.apache.atlas.catalog.VertexWrapper;
|
||||
import org.apache.atlas.catalog.definition.ResourceDefinition;
|
||||
import org.apache.atlas.repository.Constants;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.easymock.Capture;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
|
|
@ -44,7 +46,7 @@ public class AtlasEntityQueryTest {
|
|||
//todo: add tests for instance query and getInitialPipeline()
|
||||
@Test
|
||||
public void testExecute_Collection() throws Exception {
|
||||
TitanGraph graph = createStrictMock(TitanGraph.class);
|
||||
AtlasGraph graph = createStrictMock(AtlasGraph.class);
|
||||
QueryExpression expression = createStrictMock(QueryExpression.class);
|
||||
ResourceDefinition resourceDefinition = createStrictMock(ResourceDefinition.class);
|
||||
Request request = createStrictMock(Request.class);
|
||||
|
|
@ -107,7 +109,7 @@ public class AtlasEntityQueryTest {
|
|||
|
||||
@Test
|
||||
public void testExecute_Collection_rollbackOnException() throws Exception {
|
||||
TitanGraph graph = createStrictMock(TitanGraph.class);
|
||||
AtlasGraph graph = createStrictMock(AtlasGraph.class);
|
||||
QueryExpression expression = createStrictMock(QueryExpression.class);
|
||||
ResourceDefinition resourceDefinition = createStrictMock(ResourceDefinition.class);
|
||||
Request request = createStrictMock(Request.class);
|
||||
|
|
@ -151,7 +153,7 @@ public class AtlasEntityQueryTest {
|
|||
|
||||
@Test
|
||||
public void testExecute_Collection_update() throws Exception {
|
||||
TitanGraph graph = createStrictMock(TitanGraph.class);
|
||||
AtlasGraph graph = createStrictMock(AtlasGraph.class);
|
||||
QueryExpression expression = createStrictMock(QueryExpression.class);
|
||||
ResourceDefinition resourceDefinition = createStrictMock(ResourceDefinition.class);
|
||||
Request request = createStrictMock(Request.class);
|
||||
|
|
@ -227,7 +229,7 @@ public class AtlasEntityQueryTest {
|
|||
private final GremlinPipeline initialPipeline;
|
||||
private final Pipe queryPipe;
|
||||
private final Pipe notDeletedPipe;
|
||||
private final TitanGraph graph;
|
||||
private final AtlasGraph graph;
|
||||
private final VertexWrapper vWrapper;
|
||||
|
||||
public TestAtlasEntityQuery(QueryExpression queryExpression,
|
||||
|
|
@ -236,7 +238,7 @@ public class AtlasEntityQueryTest {
|
|||
GremlinPipeline initialPipeline,
|
||||
Pipe queryPipe,
|
||||
Pipe notDeletedPipe,
|
||||
TitanGraph graph,
|
||||
AtlasGraph graph,
|
||||
VertexWrapper vWrapper) {
|
||||
|
||||
super(queryExpression, resourceDefinition, request);
|
||||
|
|
@ -263,7 +265,7 @@ public class AtlasEntityQueryTest {
|
|||
}
|
||||
|
||||
@Override
|
||||
protected TitanGraph getGraph() {
|
||||
protected AtlasGraph getGraph() {
|
||||
return graph;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.utils;
|
||||
package org.apache.atlas.repository.graphdb.utils;
|
||||
|
||||
import java.util.Iterator;
|
||||
|
||||
|
|
@ -33,25 +33,20 @@
|
|||
should be configured to exclude all but the
|
||||
proper dependency
|
||||
-->
|
||||
|
||||
|
||||
<description>Apache Atlas Graph Database Implementation Dependencies</description>
|
||||
<name>Apache Atlas Graph Database Implementation Dependencies</name>
|
||||
<packaging>pom</packaging>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-titan1</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-titan0</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Additional dependencies should be added here
|
||||
as more implementations are introduced. In the
|
||||
profile corresponding to the implementation in
|
||||
the root pom.xml, all dependencies except for
|
||||
that one should be excluded. -->
|
||||
|
||||
</dependencies>
|
||||
|
||||
</project>
|
||||
|
|
|
|||
|
|
@ -19,6 +19,7 @@
|
|||
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<parent>
|
||||
<artifactId>apache-atlas</artifactId>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
|
|
@ -32,8 +33,9 @@
|
|||
|
||||
<modules>
|
||||
<module>api</module>
|
||||
<module>titan0</module>
|
||||
<module>common</module>
|
||||
<module>graphdb-impls</module>
|
||||
<module>titan0</module>
|
||||
<module>titan1</module>
|
||||
</modules>
|
||||
</project>
|
||||
|
|
|
|||
|
|
@ -34,9 +34,31 @@
|
|||
<properties>
|
||||
<tinkerpop.version>2.6.0</tinkerpop.version>
|
||||
<titan.version>0.5.4</titan.version>
|
||||
<guava.version>14.0</guava.version>
|
||||
<checkstyle.failOnViolation>false</checkstyle.failOnViolation>
|
||||
<guava.version>14.0</guava.version>
|
||||
</properties>
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>titan0</id>
|
||||
<activation>
|
||||
<activeByDefault>true</activeByDefault>
|
||||
</activation>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
<version>2.18.1</version>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<dependencies>
|
||||
|
||||
<!-- for graphdb interface definitions -->
|
||||
|
|
@ -150,7 +172,7 @@
|
|||
<plugins>
|
||||
<!--
|
||||
Create 'uber' jar that contains all of the dependencies (except those whose scope is provided)
|
||||
Only Titan 0l5l4 and its dependencies are included. The other dependencies are bundled in the war file.
|
||||
Only Titan 0.5.4 and its dependencies are included. The other dependencies are bundled in the war file.
|
||||
-->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
|
|
@ -188,7 +210,6 @@
|
|||
<shadedPattern>atlas.shaded.titan.guava</shadedPattern>
|
||||
</relocation>
|
||||
</relocations>
|
||||
<createSourcesJar>true</createSourcesJar>
|
||||
<transformers>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer"/>
|
||||
</transformers>
|
||||
|
|
|
|||
|
|
@ -45,8 +45,8 @@ import org.apache.atlas.repository.graphdb.AtlasSchemaViolationException;
|
|||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.GremlinVersion;
|
||||
import org.apache.atlas.repository.graphdb.titan0.query.Titan0GraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.utils.IteratorToIterableAdapter;
|
||||
import org.apache.atlas.typesystem.types.IDataType;
|
||||
import org.apache.atlas.utils.IteratorToIterableAdapter;
|
||||
|
||||
import com.google.common.base.Function;
|
||||
import com.google.common.collect.Iterables;
|
||||
|
|
|
|||
|
|
@ -0,0 +1,333 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Licensed to the Apache Software Foundation (ASF) under one
|
||||
~ or more contributor license agreements. See the NOTICE file
|
||||
~ distributed with this work for additional information
|
||||
~ regarding copyright ownership. The ASF licenses this file
|
||||
~ to you under the Apache License, Version 2.0 (the
|
||||
~ "License"); you may not use this file except in compliance
|
||||
~ with the License. You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<parent>
|
||||
<artifactId>atlas-graphdb</artifactId>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<version>0.8-incubating-SNAPSHOT</version>
|
||||
</parent>
|
||||
<artifactId>atlas-graphdb-titan1</artifactId>
|
||||
<description>Apache Atlas Titan 1.0.0 Graph DB Impl</description>
|
||||
<name>Apache Atlas Titan 1.0.0 GraphDB Impl</name>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<properties>
|
||||
<tinkerpop.version>3.0.1-incubating</tinkerpop.version>
|
||||
<titan.version>1.0.0</titan.version>
|
||||
<checkstyle.failOnViolation>false</checkstyle.failOnViolation>
|
||||
</properties>
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>titan1</id>
|
||||
<activation>
|
||||
<jdk>1.8</jdk>
|
||||
</activation>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-enforcer-plugin</artifactId>
|
||||
<version>1.4.1</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>enforce-java-8</id>
|
||||
<goals>
|
||||
<goal>enforce</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<rules>
|
||||
<requireJavaVersion>
|
||||
<version>1.8.0</version>
|
||||
</requireJavaVersion>
|
||||
<requireMavenVersion>
|
||||
<version>3.1.0</version>
|
||||
</requireMavenVersion>
|
||||
</rules>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
<version>2.18.1</version>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.1</version>
|
||||
<configuration>
|
||||
<skipMain>false</skipMain>
|
||||
<skip>false</skip>
|
||||
<excludes>
|
||||
<exclude>org.apache.atlas</exclude>
|
||||
</excludes>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
<properties>
|
||||
<graphdb.backend.impl>org.apache.atlas.repository.graphdb.titan1.Titan1GraphDatabase</graphdb.backend.impl>
|
||||
</properties>
|
||||
</profile>
|
||||
</profiles>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-common</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-api</artifactId>
|
||||
<!-- set scope to provided to prevent the this from being included in the shared jar -->
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.google.inject</groupId>
|
||||
<artifactId>guice</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>commons-configuration</groupId>
|
||||
<artifactId>commons-configuration</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
|
||||
<!-- https://mvnrepository.com/artifact/com.thinkaurelius.titan/titan-hbase -->
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-hbase</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-core</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-solr</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
<!-- this conflicts with the servlet api version that Atlas needs -->
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>javax.servlet</groupId>
|
||||
<artifactId>servlet-api</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.hbase</groupId>
|
||||
<artifactId>hbase-client</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.vividsolutions</groupId>
|
||||
<artifactId>jts</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.solr</groupId>
|
||||
<artifactId>solr-core</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.solr</groupId>
|
||||
<artifactId>solr-solrj</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-es</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-berkeleyje</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-lucene</artifactId>
|
||||
<version>${titan.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.testng</groupId>
|
||||
<artifactId>testng</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.mockito</groupId>
|
||||
<artifactId>mockito-all</artifactId>
|
||||
</dependency>
|
||||
|
||||
<!-- titan 1 requires guava 18.0 -->
|
||||
<dependency>
|
||||
<groupId>com.google.guava</groupId>
|
||||
<artifactId>guava</artifactId>
|
||||
<version>18.0</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Graph DB -->
|
||||
<dependency>
|
||||
<groupId>org.apache.tinkerpop</groupId>
|
||||
<artifactId>gremlin-core</artifactId>
|
||||
<version>3.0.1-incubating</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.tinkerpop</groupId>
|
||||
<artifactId>tinkergraph-gremlin</artifactId>
|
||||
<version>3.0.1-incubating</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<plugins>
|
||||
<!-- Skip the compilation of code and tests by default. Titan 1 code will be compiled only when titan1 profile is explicitly enabled. -->
|
||||
<plugin>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<version>3.1</version>
|
||||
<configuration>
|
||||
<skipMain>true</skipMain>
|
||||
<skip>true</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
<version>2.18.1</version>
|
||||
<configuration>
|
||||
<skip>true</skip>
|
||||
<skipTests>true</skipTests>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<!--
|
||||
Create 'uber' jar that contains all of the dependencies (except those whose scope is provided)
|
||||
Only titan 1 and its dependencies are included. The other dependencies are bundled in the war file.
|
||||
|
||||
We also relocate the Google guava packages to avoid conflicts with Atlas code which depends on Guava 14
|
||||
-->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-shade-plugin</artifactId>
|
||||
<version>2.4.3</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<phase>package</phase>
|
||||
<goals>
|
||||
<goal>shade</goal>
|
||||
</goals>
|
||||
<configuration>
|
||||
<shadedArtifactAttached>false</shadedArtifactAttached>
|
||||
<artifactSet>
|
||||
<excludes>
|
||||
<!-- these are bundled with Atlas -->
|
||||
<exclude>org.slf4j:*</exclude>
|
||||
</excludes>
|
||||
</artifactSet>
|
||||
<relocations>
|
||||
<relocation>
|
||||
<pattern>com.google.common</pattern>
|
||||
<shadedPattern>org.apache.atlas.shaded.com.google.common</shadedPattern>
|
||||
</relocation>
|
||||
</relocations>
|
||||
<!-- disable generation of sources jar due to clash with maven-source-plugin -->
|
||||
<!-- <createSourcesJar>true</createSourcesJar> -->
|
||||
<transformers>
|
||||
<transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer" />
|
||||
</transformers>
|
||||
</configuration>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-core</artifactId>
|
||||
<version>1.0.0</version>
|
||||
<exclusions>
|
||||
<!-- rexster does not work with servlet-api -->
|
||||
<exclusion>
|
||||
<groupId>com.tinkerpop.rexster</groupId>
|
||||
<artifactId>rexster-core</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>com.tinkerpop.rexster</groupId>
|
||||
<artifactId>rexster-server</artifactId>
|
||||
</exclusion>
|
||||
<!-- asm 4.0 does not work with jersey asm 3.1 -->
|
||||
<exclusion>
|
||||
<groupId>com.tinkerpop</groupId>
|
||||
<artifactId>frames</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>com.esotericsoftware.reflectasm</groupId>
|
||||
<artifactId>reflectasm</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.ow2.asm</groupId>
|
||||
<artifactId>asm</artifactId>
|
||||
</exclusion>
|
||||
<exclusion> <!-- GPL license imported from ganglia -->
|
||||
<groupId>org.acplt</groupId>
|
||||
<artifactId>oncrpc</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-berkeleyje</artifactId>
|
||||
<version>1.0.0</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-hbase</artifactId>
|
||||
<version>1.0.0</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-solr</artifactId>
|
||||
<version>1.0.0</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
</dependencyManagement>
|
||||
</project>
|
||||
|
|
@ -0,0 +1,87 @@
|
|||
==================
|
||||
Titan 1.0.0 README
|
||||
==================
|
||||
|
||||
IMPORTANT: Titan 1 support in Atlas is currently a work in progress.
|
||||
|
||||
|
||||
ARCHITECTURE NOTES
|
||||
------------------
|
||||
|
||||
The build is currently set up to include only one of the graph backends in the Atlas war file. The configured graph
|
||||
backend is determined by maven profile. The default profile is titan0. To build Atlas configured to run against Titan 1,
|
||||
the titan1 profile must be enabled. Titan1 project has support for Gremlin3. Gremlin Translator translates the DSL to
|
||||
gremlin3 compliant syntax when titan1 is configured as backend graph db.
|
||||
|
||||
|
||||
REQUIREMENTS
|
||||
--------------
|
||||
|
||||
Titan 1 requires Java 8 to be used both when building and running Atlas. While building on Java7, the java classes in
|
||||
the Titan 1 project are not compiled. But an empty jar is produced. If java 8 is used, then titan 1 classes are compiled
|
||||
but tests are only executed if titan1 profile is explicitly enabled.
|
||||
|
||||
|
||||
|
||||
USING ATLAS WITH TITAN 1
|
||||
------------------------
|
||||
|
||||
1) Build Atlas with the titan1 maven profile enabled:
|
||||
|
||||
mvn install -P dist -P titan1
|
||||
|
||||
Note that there are some tests in repository and webapp project which are skipped when running with the titan1 profile.
|
||||
Please refer to known issues section below.
|
||||
|
||||
This will build Atlas and run all of the tests against Titan 1. Only Atlas builds that were generated with the titan1
|
||||
maven profile enabled can be used to use Atlas with Titan 1.
|
||||
|
||||
2) Configure the Atlas runtime to use Titan 1 by setting the atlas.graphdb.backend property in
|
||||
ATLAS_HOME/conf/atlas-application.properties, as follows:
|
||||
|
||||
atlas.graphdb.backend=org.apache.atlas.repository.graphdb.titan1.Titan1GraphDatabase
|
||||
|
||||
3) Attempt to start the Atlas server. NOTE: As of this writing, Atlas fails to start (see issue 2 below).
|
||||
|
||||
|
||||
KNOWN ISSUES
|
||||
------------
|
||||
|
||||
1) EntityLineageService is hard-coded to generate Gremlin that is specific to Tinker Pop 2. It needs to be updated to
|
||||
use GremlinExpressionFactory to generate Gremlin that is appropriate for the version of Titan being used. Currently
|
||||
these tests are skipped when the titan1 profile is enabled.
|
||||
|
||||
https://issues.apache.org/jira/browse/ATLAS-1579
|
||||
|
||||
2) Catalog project is hard-coded to generate Gremlin that is specific to Tinker Pop 2. It needs to be updated to use
|
||||
GremlinExpressionFactory to generate Gremlin that is appropriate for the version of Titan being used. In addition, it
|
||||
has direct dependencies on titan 0 / Tinker Pop 2 classes.
|
||||
|
||||
https://issues.apache.org/jira/browse/ATLAS-1580
|
||||
|
||||
3) The Atlas war file startup is currently failing when Titan1 is being used. Due to the titan 0 dependencies in
|
||||
catalog, the catalog jar is currently being excluded from webapp when titan1 is being used. However, Atlas appears to
|
||||
have runtime dependencies on the stuff in Catalog. The war startup currently fails with the following exception:
|
||||
|
||||
Caused by: java.lang.ClassNotFoundException: org.apache.atlas.catalog.exception.CatalogException
|
||||
at org.codehaus.plexus.classworlds.strategy.SelfFirstStrategy.loadClass(SelfFirstStrategy.java:50)
|
||||
at org.codehaus.plexus.classworlds.realm.ClassRealm.unsynchronizedLoadClass(ClassRealm.java:271)
|
||||
|
||||
https://issues.apache.org/jira/browse/ATLAS-1581
|
||||
|
||||
4) There are some known test failures in webapp project. Those need to be addressed. There is work needed to refactor
|
||||
webapp so that it can function without catalog until issue #2 above is resolved.
|
||||
|
||||
https://issues.apache.org/jira/browse/ATLAS-1582
|
||||
|
||||
5) We cannot bundle both titan0 and titan1 in the Atlas war file because titan1 and titan0 require different versions of
|
||||
the same libraries. We cannot have multiple versions of the same library on the classpath. Another issue there is that
|
||||
Gremin queries are executed via the java services mechanism. Specifically, the titan 1 implemention bundles a file
|
||||
called javax.script.ScriptingEngineFactory, which tells Java to
|
||||
use org.apache.tinkerpop.gremlin.groovy.jsr223.GremlinGroovyScriptEngineFactory. We cannot have this file on the
|
||||
classpath when using titan 0 since it would cause the Titan 0 implemention to try to execute queries using TP 3. There
|
||||
may be ways of working around this, such as making Titan1Graph and Titan0Graph explicitly instantiate the
|
||||
GremlinGroovyScriptEngineFactory. This was not investigated very much, though. If we combine that with shading
|
||||
Titan0/1 and all of their dependencies, we might be able to bundle both the Titan 1 and Titan 0 implementations in the
|
||||
Atlas war file and have things work correctly for both versions. Another possibility would be to use a custom
|
||||
classloader to load the correct atlas-graphdb-titan0/1 jar during Atlas startup based on the configuration.
|
||||
|
|
@ -0,0 +1,118 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphIndex;
|
||||
import org.apache.atlas.repository.graphdb.titan1.query.Titan1GraphQuery;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
import org.apache.tinkerpop.gremlin.structure.Vertex;
|
||||
|
||||
import com.thinkaurelius.titan.core.Cardinality;
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
import com.thinkaurelius.titan.core.schema.TitanGraphIndex;
|
||||
|
||||
|
||||
/**
|
||||
* Factory that serves up instances of graph database abstraction layer classes
|
||||
* that correspond to Titan/Tinkerpop3 classes.
|
||||
*/
|
||||
public final class GraphDbObjectFactory {
|
||||
|
||||
private GraphDbObjectFactory() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a Titan1Edge that corresponds to the given Gremlin Edge.
|
||||
*
|
||||
* @param graph The graph the edge should be created in
|
||||
* @param source The gremlin edge
|
||||
*/
|
||||
public static Titan1Edge createEdge(Titan1Graph graph, Edge source) {
|
||||
|
||||
if (source == null) {
|
||||
return null;
|
||||
}
|
||||
return new Titan1Edge(graph, source);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a Titan1GraphQuery that corresponds to the given GraphQuery.
|
||||
*
|
||||
* @param graph the graph that is being quried
|
||||
*/
|
||||
public static Titan1GraphQuery createQuery(Titan1Graph graph, boolean isChildQuery) {
|
||||
|
||||
return new Titan1GraphQuery(graph, isChildQuery);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a Titan1Vertex that corresponds to the given Gremlin Vertex.
|
||||
*
|
||||
* @param graph The graph that contains the vertex
|
||||
* @param source the Gremlin vertex
|
||||
*/
|
||||
public static Titan1Vertex createVertex(Titan1Graph graph, Vertex source) {
|
||||
|
||||
if (source == null) {
|
||||
return null;
|
||||
}
|
||||
return new Titan1Vertex(graph, source);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param propertyKey The Gremlin propertyKey.
|
||||
*
|
||||
*/
|
||||
public static Titan1PropertyKey createPropertyKey(PropertyKey propertyKey) {
|
||||
if (propertyKey == null) {
|
||||
return null;
|
||||
}
|
||||
return new Titan1PropertyKey(propertyKey);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param index The gremlin index.
|
||||
* @return
|
||||
*/
|
||||
public static AtlasGraphIndex createGraphIndex(TitanGraphIndex index) {
|
||||
if (index == null) {
|
||||
return null;
|
||||
}
|
||||
return new Titan1GraphIndex(index);
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts a Multiplicity to a Cardinality.
|
||||
*
|
||||
* @param cardinality
|
||||
* @return
|
||||
*/
|
||||
public static AtlasCardinality createCardinality(Cardinality cardinality) {
|
||||
|
||||
if (cardinality == Cardinality.SINGLE) {
|
||||
return AtlasCardinality.SINGLE;
|
||||
} else if (cardinality == Cardinality.LIST) {
|
||||
return AtlasCardinality.LIST;
|
||||
}
|
||||
return AtlasCardinality.SET;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,54 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasEdge.
|
||||
*/
|
||||
public class Titan1Edge extends Titan1Element<Edge> implements AtlasEdge<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
|
||||
public Titan1Edge(Titan1Graph graph, Edge edge) {
|
||||
super(graph, edge);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getLabel() {
|
||||
return getWrappedElement().label();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Titan1Edge getE() {
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> getInVertex() {
|
||||
return GraphDbObjectFactory.createVertex(graph, getWrappedElement().inVertex());
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> getOutVertex() {
|
||||
return GraphDbObjectFactory.createVertex(graph, getWrappedElement().outVertex());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,258 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasElement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasSchemaViolationException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.titan1.graphson.AtlasGraphSONMode;
|
||||
import org.apache.atlas.repository.graphdb.titan1.graphson.AtlasGraphSONUtility;
|
||||
import org.apache.tinkerpop.gremlin.structure.Element;
|
||||
import org.apache.tinkerpop.gremlin.structure.Property;
|
||||
import org.codehaus.jettison.json.JSONException;
|
||||
import org.codehaus.jettison.json.JSONObject;
|
||||
|
||||
import com.google.common.base.Function;
|
||||
import com.google.common.collect.Lists;
|
||||
import com.thinkaurelius.titan.core.SchemaViolationException;
|
||||
import com.thinkaurelius.titan.core.TitanElement;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasElement.
|
||||
*
|
||||
* @param <T> the implementation class of the wrapped Titan 1 element
|
||||
* that is stored.
|
||||
*/
|
||||
public class Titan1Element<T extends Element> implements AtlasElement {
|
||||
|
||||
|
||||
private T element;
|
||||
protected Titan1Graph graph;
|
||||
|
||||
public Titan1Element(Titan1Graph graph, T element) {
|
||||
this.element = element;
|
||||
this.graph = graph;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T getProperty(String propertyName, Class<T> clazz) {
|
||||
|
||||
//add explicit logic to return null if the property does not exist
|
||||
//This is the behavior Atlas expects. Titan 1 throws an exception
|
||||
//in this scenario.
|
||||
Property p = getWrappedElement().property(propertyName);
|
||||
if (p.isPresent()) {
|
||||
Object propertyValue= p.value();
|
||||
if (propertyValue == null) {
|
||||
return null;
|
||||
}
|
||||
if (AtlasEdge.class == clazz) {
|
||||
return (T)graph.getEdge(propertyValue.toString());
|
||||
}
|
||||
if (AtlasVertex.class == clazz) {
|
||||
return (T)graph.getVertex(propertyValue.toString());
|
||||
}
|
||||
return (T)propertyValue;
|
||||
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Gets all of the values of the given property.
|
||||
* @param propertyName
|
||||
* @return
|
||||
*/
|
||||
@Override
|
||||
public <T> Collection<T> getPropertyValues(String propertyName, Class<T> type) {
|
||||
return Collections.singleton(getProperty(propertyName, type));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<String> getPropertyKeys() {
|
||||
return getWrappedElement().keys();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeProperty(String propertyName) {
|
||||
Iterator<? extends Property<String>> it = getWrappedElement().properties(propertyName);
|
||||
while(it.hasNext()) {
|
||||
Property<String> property = it.next();
|
||||
property.remove();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setProperty(String propertyName, Object value) {
|
||||
try {
|
||||
getWrappedElement().property(propertyName, value);
|
||||
} catch(SchemaViolationException e) {
|
||||
throw new AtlasSchemaViolationException(e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getId() {
|
||||
return element.id();
|
||||
}
|
||||
|
||||
|
||||
//not in interface
|
||||
public T getWrappedElement() {
|
||||
return element;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public JSONObject toJson(Set<String> propertyKeys) throws JSONException {
|
||||
|
||||
return AtlasGraphSONUtility.jsonFromElement(this, propertyKeys, AtlasGraphSONMode.NORMAL);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = 37;
|
||||
result = 17*result + getClass().hashCode();
|
||||
result = 17*result + getWrappedElement().hashCode();
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
|
||||
if (other == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (other.getClass() != getClass()) {
|
||||
return false;
|
||||
}
|
||||
Titan1Element otherElement = (Titan1Element) other;
|
||||
return getWrappedElement().equals(otherElement.getWrappedElement());
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<String> getListProperty(String propertyName) {
|
||||
List<String> value = getProperty(propertyName, List.class);
|
||||
if (value == null) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setListProperty(String propertyName, List<String> values) {
|
||||
setProperty(propertyName, values);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean exists() {
|
||||
try {
|
||||
return !((TitanElement)element).isRemoved();
|
||||
} catch(IllegalStateException e) {
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> void setJsonProperty(String propertyName, T value) {
|
||||
setProperty(propertyName, value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T getJsonProperty(String propertyName) {
|
||||
return (T)getProperty(propertyName, String.class);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getIdForDisplay() {
|
||||
return getId().toString();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public <V> List<V> getListProperty(String propertyName, Class<V> elementType) {
|
||||
|
||||
List<String> value = getListProperty(propertyName);
|
||||
|
||||
if (value.isEmpty()) {
|
||||
return (List<V>)value;
|
||||
}
|
||||
|
||||
if (AtlasEdge.class.isAssignableFrom(elementType)) {
|
||||
|
||||
|
||||
return (List<V>)Lists.transform(value, new Function<String, AtlasEdge>(){
|
||||
|
||||
@Override
|
||||
public AtlasEdge apply(String input) {
|
||||
return graph.getEdge(input);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
if (AtlasVertex.class.isAssignableFrom(elementType)) {
|
||||
|
||||
return (List<V>)Lists.transform(value, new Function<String, AtlasVertex>(){
|
||||
|
||||
@Override
|
||||
public AtlasVertex apply(String input) {
|
||||
return graph.getVertex(input);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return (List<V>)value;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void setPropertyFromElementsIds(String propertyName, List<AtlasElement> values) {
|
||||
List<String> propertyValue = new ArrayList<>(values.size());
|
||||
for(AtlasElement value: values) {
|
||||
propertyValue.add(value.getId().toString());
|
||||
}
|
||||
setProperty(propertyName, propertyValue);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void setPropertyFromElementId(String propertyName, AtlasElement value) {
|
||||
setProperty(propertyName, value.getId().toString());
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isIdAssigned() {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,405 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.OutputStream;
|
||||
import java.util.Collection;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.script.Bindings;
|
||||
import javax.script.ScriptEngine;
|
||||
import javax.script.ScriptException;
|
||||
|
||||
import org.apache.atlas.groovy.GroovyExpression;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphManagement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.AtlasIndexQuery;
|
||||
import org.apache.atlas.repository.graphdb.AtlasSchemaViolationException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.GremlinVersion;
|
||||
import org.apache.atlas.repository.graphdb.titan1.query.Titan1GraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.utils.IteratorToIterableAdapter;
|
||||
import org.apache.atlas.typesystem.types.IDataType;
|
||||
import org.apache.tinkerpop.gremlin.groovy.CompilerCustomizerProvider;
|
||||
import org.apache.tinkerpop.gremlin.groovy.DefaultImportCustomizerProvider;
|
||||
import org.apache.tinkerpop.gremlin.groovy.jsr223.GremlinGroovyScriptEngine;
|
||||
import org.apache.tinkerpop.gremlin.process.traversal.P;
|
||||
import org.apache.tinkerpop.gremlin.process.traversal.dsl.graph.__;
|
||||
import org.apache.tinkerpop.gremlin.process.traversal.step.util.ImmutablePath;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
import org.apache.tinkerpop.gremlin.structure.Element;
|
||||
import org.apache.tinkerpop.gremlin.structure.Vertex;
|
||||
import org.apache.tinkerpop.gremlin.structure.io.IoCore;
|
||||
import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
|
||||
import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONWriter;
|
||||
|
||||
import com.google.common.base.Function;
|
||||
import com.google.common.collect.Iterables;
|
||||
import com.google.common.collect.Lists;
|
||||
import com.google.common.collect.Maps;
|
||||
import com.thinkaurelius.titan.core.Cardinality;
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
import com.thinkaurelius.titan.core.SchemaViolationException;
|
||||
import com.thinkaurelius.titan.core.TitanGraph;
|
||||
import com.thinkaurelius.titan.core.TitanIndexQuery;
|
||||
import com.thinkaurelius.titan.core.schema.TitanGraphIndex;
|
||||
import com.thinkaurelius.titan.core.schema.TitanManagement;
|
||||
import com.thinkaurelius.titan.core.util.TitanCleanup;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasGraph.
|
||||
*/
|
||||
public class Titan1Graph implements AtlasGraph<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
private final ConvertGremlinValueFunction GREMLIN_VALUE_CONVERSION_FUNCTION = new ConvertGremlinValueFunction();
|
||||
|
||||
private final class ConvertGremlinValueFunction implements Function<Object, Object> {
|
||||
@Override
|
||||
public Object apply(Object input) {
|
||||
return convertGremlinValue(input);
|
||||
}
|
||||
}
|
||||
|
||||
private final Set<String> multiProperties;
|
||||
|
||||
public Titan1Graph() {
|
||||
//determine multi-properties once at startup
|
||||
TitanManagement mgmt = null;
|
||||
try {
|
||||
mgmt = Titan1GraphDatabase.getGraphInstance().openManagement();
|
||||
Iterable<PropertyKey> keys = mgmt.getRelationTypes(PropertyKey.class);
|
||||
multiProperties = new HashSet<>();
|
||||
for (PropertyKey key : keys) {
|
||||
if (key.cardinality() != Cardinality.SINGLE) {
|
||||
multiProperties.add(key.name());
|
||||
}
|
||||
}
|
||||
} finally {
|
||||
if (mgmt != null) {
|
||||
mgmt.rollback();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasEdge<Titan1Vertex, Titan1Edge> addEdge(AtlasVertex<Titan1Vertex, Titan1Edge> outVertex,
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> inVertex,
|
||||
String edgeLabel) {
|
||||
|
||||
try {
|
||||
Vertex oV = outVertex.getV().getWrappedElement();
|
||||
Vertex iV = inVertex.getV().getWrappedElement();
|
||||
Edge edge = oV.addEdge(edgeLabel, iV);
|
||||
return GraphDbObjectFactory.createEdge(this, edge);
|
||||
} catch (SchemaViolationException e) {
|
||||
throw new AtlasSchemaViolationException(e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasGraphQuery<Titan1Vertex, Titan1Edge> query() {
|
||||
return new Titan1GraphQuery(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasEdge<Titan1Vertex, Titan1Edge> getEdge(String edgeId) {
|
||||
Iterator<Edge> it = getGraph().edges(edgeId);
|
||||
Edge e = getSingleElement(it, edgeId);
|
||||
return GraphDbObjectFactory.createEdge(this, e);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeEdge(AtlasEdge<Titan1Vertex, Titan1Edge> edge) {
|
||||
|
||||
Edge wrapped = edge.getE().getWrappedElement();
|
||||
wrapped.remove();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeVertex(AtlasVertex<Titan1Vertex, Titan1Edge> vertex) {
|
||||
Vertex wrapped = vertex.getV().getWrappedElement();
|
||||
wrapped.remove();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> getEdges() {
|
||||
|
||||
Iterator<Edge> edges = getGraph().edges();
|
||||
return wrapEdges(edges);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> getVertices() {
|
||||
|
||||
Iterator<Vertex> vertices = getGraph().vertices();
|
||||
return wrapVertices(vertices);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> addVertex() {
|
||||
Vertex result = getGraph().addVertex();
|
||||
return GraphDbObjectFactory.createVertex(this, result);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void commit() {
|
||||
getGraph().tx().commit();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void rollback() {
|
||||
getGraph().tx().rollback();
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasIndexQuery<Titan1Vertex, Titan1Edge> indexQuery(String fulltextIndex, String graphQuery) {
|
||||
TitanIndexQuery query = getGraph().indexQuery(fulltextIndex, graphQuery);
|
||||
return new Titan1IndexQuery(this, query);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasGraphManagement getManagementSystem() {
|
||||
return new Titan1GraphManagement(this, getGraph().openManagement());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shutdown() {
|
||||
getGraph().close();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<String> getEdgeIndexKeys() {
|
||||
return getIndexKeys(Edge.class);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<String> getVertexIndexKeys() {
|
||||
return getIndexKeys(Vertex.class);
|
||||
}
|
||||
|
||||
private Set<String> getIndexKeys(Class<? extends Element> titanElementClass) {
|
||||
|
||||
TitanManagement mgmt = getGraph().openManagement();
|
||||
Iterable<TitanGraphIndex> indices = mgmt.getGraphIndexes(titanElementClass);
|
||||
Set<String> result = new HashSet<String>();
|
||||
for (TitanGraphIndex index : indices) {
|
||||
result.add(index.name());
|
||||
}
|
||||
mgmt.commit();
|
||||
return result;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> getVertex(String vertexId) {
|
||||
Iterator<Vertex> it = getGraph().vertices(vertexId);
|
||||
Vertex vertex = getSingleElement(it, vertexId);
|
||||
return GraphDbObjectFactory.createVertex(this, vertex);
|
||||
}
|
||||
|
||||
public static <T> T getSingleElement(Iterator<T> it, String id) {
|
||||
if (!it.hasNext()) {
|
||||
return null;
|
||||
}
|
||||
T element = it.next();
|
||||
if (it.hasNext()) {
|
||||
throw new RuntimeException("Multiple items were found with the id " + id);
|
||||
}
|
||||
return element;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> getVertices(String key, Object value) {
|
||||
AtlasGraphQuery<Titan1Vertex, Titan1Edge> query = query();
|
||||
query.has(key, value);
|
||||
return query.vertices();
|
||||
}
|
||||
|
||||
private Object convertGremlinValue(Object rawValue) {
|
||||
|
||||
if (rawValue instanceof Vertex) {
|
||||
return GraphDbObjectFactory.createVertex(this, (Vertex) rawValue);
|
||||
} else if (rawValue instanceof Edge) {
|
||||
return GraphDbObjectFactory.createEdge(this, (Edge) rawValue);
|
||||
} else if (rawValue instanceof Map) {
|
||||
Map<String,Object> rowValue = (Map<String,Object>)rawValue;
|
||||
return Maps.transformValues(rowValue, GREMLIN_VALUE_CONVERSION_FUNCTION);
|
||||
} else if (rawValue instanceof ImmutablePath) {
|
||||
ImmutablePath path = (ImmutablePath) rawValue;
|
||||
return convertGremlinValue(path.objects());
|
||||
}
|
||||
else if (rawValue instanceof List) {
|
||||
return Lists.transform((List)rawValue, GREMLIN_VALUE_CONVERSION_FUNCTION);
|
||||
} else if (rawValue instanceof Collection) {
|
||||
throw new UnsupportedOperationException("Unhandled collection type: " + rawValue.getClass());
|
||||
}
|
||||
return rawValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public GremlinVersion getSupportedGremlinVersion() {
|
||||
|
||||
return GremlinVersion.THREE;
|
||||
}
|
||||
@Override
|
||||
public void clear() {
|
||||
TitanGraph graph = getGraph();
|
||||
if (graph.isOpen()) {
|
||||
// only a shut down graph can be cleared
|
||||
graph.close();
|
||||
}
|
||||
TitanCleanup.clear(graph);
|
||||
}
|
||||
|
||||
private TitanGraph getGraph() {
|
||||
return Titan1GraphDatabase.getGraphInstance();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void exportToGson(OutputStream os) throws IOException {
|
||||
|
||||
GraphSONMapper mapper = getGraph().io(IoCore.graphson()).mapper().create();
|
||||
GraphSONWriter.Builder builder = GraphSONWriter.build();
|
||||
builder.mapper(mapper);
|
||||
GraphSONWriter writer = builder.create();
|
||||
writer.writeGraph(os, getGraph());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object executeGremlinScript(String query, boolean isPath) throws ScriptException {
|
||||
|
||||
Object result = executeGremlinScript(query);
|
||||
return convertGremlinValue(result);
|
||||
}
|
||||
|
||||
private Object executeGremlinScript(String gremlinQuery) throws ScriptException {
|
||||
|
||||
Set<String> extraImports = new HashSet<String>();
|
||||
extraImports.add(java.util.function.Function.class.getName());
|
||||
|
||||
Set<String> extraStaticImports = new HashSet<String>();
|
||||
extraStaticImports.add(P.class.getName() + ".*");
|
||||
extraStaticImports.add(__.class.getName() + ".*");
|
||||
CompilerCustomizerProvider provider = new DefaultImportCustomizerProvider(extraImports, extraStaticImports);
|
||||
|
||||
GremlinGroovyScriptEngine scriptEngine = new GremlinGroovyScriptEngine(provider);
|
||||
try {
|
||||
Bindings bindings = scriptEngine.createBindings();
|
||||
bindings.put("graph", getGraph());
|
||||
bindings.put("g", getGraph().traversal());
|
||||
Object result = scriptEngine.eval(gremlinQuery, bindings);
|
||||
return result;
|
||||
} finally {
|
||||
try {
|
||||
scriptEngine.close();
|
||||
} catch (Exception e) {
|
||||
throw new ScriptException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object executeGremlinScript(ScriptEngine scriptEngine,
|
||||
Bindings bindings, String query, boolean isPath)
|
||||
throws ScriptException {
|
||||
|
||||
if(!bindings.containsKey("g")) {
|
||||
bindings.put("g", getGraph());
|
||||
}
|
||||
Object result = scriptEngine.eval(query, bindings);
|
||||
return convertGremlinValue(result);
|
||||
}
|
||||
|
||||
@Override
|
||||
public GroovyExpression generatePersisentToLogicalConversionExpression(GroovyExpression expr, IDataType<?> type) {
|
||||
//nothing special needed, value is stored in required type
|
||||
return expr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isPropertyValueConversionNeeded(IDataType<?> type) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean requiresInitialIndexedPredicate() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public GroovyExpression getInitialIndexedPredicate(GroovyExpression parent) {
|
||||
return parent;
|
||||
}
|
||||
|
||||
@Override
|
||||
public GroovyExpression addOutputTransformationPredicate(GroovyExpression expr, boolean isSelect, boolean isPath) {
|
||||
return expr;
|
||||
}
|
||||
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> wrapEdges(Iterator<Edge> it) {
|
||||
Iterable<Edge> iterable = new IteratorToIterableAdapter<Edge>(it);
|
||||
return wrapEdges(iterable);
|
||||
}
|
||||
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> wrapVertices(Iterator<? extends Vertex> it) {
|
||||
Iterable<? extends Vertex> iterable = new IteratorToIterableAdapter<>(it);
|
||||
return wrapVertices(iterable);
|
||||
}
|
||||
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> wrapVertices(Iterable<? extends Vertex> it) {
|
||||
|
||||
return Iterables.transform(it, new Function<Vertex, AtlasVertex<Titan1Vertex, Titan1Edge>>() {
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> apply(Vertex input) {
|
||||
return GraphDbObjectFactory.createVertex(Titan1Graph.this, input);
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> wrapEdges(Iterable<Edge> it) {
|
||||
Iterable<Edge> result = (Iterable<Edge>) it;
|
||||
return Iterables.transform(result, new Function<Edge, AtlasEdge<Titan1Vertex, Titan1Edge>>() {
|
||||
|
||||
@Override
|
||||
public AtlasEdge<Titan1Vertex, Titan1Edge> apply(Edge input) {
|
||||
return GraphDbObjectFactory.createEdge(Titan1Graph.this, input);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isMultiProperty(String propertyName) {
|
||||
return multiProperties.contains(propertyName);
|
||||
}
|
||||
|
||||
public void addMultiProperties(Set<String> names) {
|
||||
multiProperties.addAll(names);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,176 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.math.BigInteger;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.apache.atlas.ApplicationProperties;
|
||||
import org.apache.atlas.AtlasException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.GraphDatabase;
|
||||
import org.apache.atlas.repository.graphdb.titan1.serializer.BigDecimalSerializer;
|
||||
import org.apache.atlas.repository.graphdb.titan1.serializer.BigIntegerSerializer;
|
||||
import org.apache.atlas.repository.graphdb.titan1.serializer.StringListSerializer;
|
||||
import org.apache.atlas.repository.graphdb.titan1.serializer.TypeCategorySerializer;
|
||||
import org.apache.atlas.typesystem.types.DataTypes.TypeCategory;
|
||||
import org.apache.commons.configuration.Configuration;
|
||||
import org.apache.tinkerpop.gremlin.groovy.loaders.SugarLoader;
|
||||
import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import com.thinkaurelius.titan.core.TitanFactory;
|
||||
import com.thinkaurelius.titan.core.TitanGraph;
|
||||
import com.thinkaurelius.titan.core.schema.TitanManagement;
|
||||
import com.thinkaurelius.titan.core.util.TitanCleanup;
|
||||
import com.thinkaurelius.titan.graphdb.tinkerpop.TitanIoRegistry;
|
||||
|
||||
/**
|
||||
* Default implementation for Graph Provider that doles out Titan Graph.
|
||||
*/
|
||||
public class Titan1GraphDatabase implements GraphDatabase<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(Titan1GraphDatabase.class);
|
||||
|
||||
/**
|
||||
* Constant for the configuration property that indicates the prefix.
|
||||
*/
|
||||
public static final String GRAPH_PREFIX = "atlas.graph";
|
||||
|
||||
public static final String INDEX_BACKEND_CONF = "index.search.backend";
|
||||
|
||||
public static final String INDEX_BACKEND_LUCENE = "lucene";
|
||||
|
||||
public static final String INDEX_BACKEND_ES = "elasticsearch";
|
||||
|
||||
private static volatile Titan1Graph atlasGraphInstance = null;
|
||||
private static volatile TitanGraph graphInstance;
|
||||
|
||||
public Titan1GraphDatabase() {
|
||||
|
||||
//update registry
|
||||
GraphSONMapper.build().addRegistry(TitanIoRegistry.INSTANCE).create();
|
||||
}
|
||||
|
||||
public static Configuration getConfiguration() throws AtlasException {
|
||||
Configuration configProperties = ApplicationProperties.get();
|
||||
|
||||
Configuration titanConfig = ApplicationProperties.getSubsetConfiguration(configProperties, GRAPH_PREFIX);
|
||||
|
||||
//add serializers for non-standard property value types that Atlas uses
|
||||
|
||||
titanConfig.addProperty("attributes.custom.attribute1.attribute-class", TypeCategory.class.getName());
|
||||
titanConfig.addProperty("attributes.custom.attribute1.serializer-class",
|
||||
TypeCategorySerializer.class.getName());
|
||||
|
||||
//not ideal, but avoids making large changes to Atlas
|
||||
titanConfig.addProperty("attributes.custom.attribute2.attribute-class", ArrayList.class.getName());
|
||||
titanConfig.addProperty("attributes.custom.attribute2.serializer-class", StringListSerializer.class.getName());
|
||||
|
||||
titanConfig.addProperty("attributes.custom.attribute3.attribute-class", BigInteger.class.getName());
|
||||
titanConfig.addProperty("attributes.custom.attribute3.serializer-class", BigIntegerSerializer.class.getName());
|
||||
|
||||
titanConfig.addProperty("attributes.custom.attribute4.attribute-class", BigDecimal.class.getName());
|
||||
titanConfig.addProperty("attributes.custom.attribute4.serializer-class", BigDecimalSerializer.class.getName());
|
||||
|
||||
return titanConfig;
|
||||
}
|
||||
|
||||
public static TitanGraph getGraphInstance() {
|
||||
if (graphInstance == null) {
|
||||
synchronized (Titan1GraphDatabase.class) {
|
||||
if (graphInstance == null) {
|
||||
Configuration config;
|
||||
try {
|
||||
config = getConfiguration();
|
||||
} catch (AtlasException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
|
||||
graphInstance = TitanFactory.open(config);
|
||||
atlasGraphInstance = new Titan1Graph();
|
||||
validateIndexBackend(config);
|
||||
}
|
||||
}
|
||||
}
|
||||
return graphInstance;
|
||||
}
|
||||
|
||||
public static void unload() {
|
||||
synchronized (Titan1GraphDatabase.class) {
|
||||
|
||||
if (graphInstance == null) {
|
||||
return;
|
||||
}
|
||||
graphInstance.tx().commit();
|
||||
graphInstance.close();
|
||||
graphInstance = null;
|
||||
}
|
||||
}
|
||||
|
||||
static void validateIndexBackend(Configuration config) {
|
||||
String configuredIndexBackend = config.getString(INDEX_BACKEND_CONF);
|
||||
|
||||
TitanManagement managementSystem = getGraphInstance().openManagement();
|
||||
String currentIndexBackend = managementSystem.get(INDEX_BACKEND_CONF);
|
||||
managementSystem.commit();
|
||||
|
||||
if (!configuredIndexBackend.equals(currentIndexBackend)) {
|
||||
throw new RuntimeException("Configured Index Backend " + configuredIndexBackend
|
||||
+ " differs from earlier configured Index Backend " + currentIndexBackend + ". Aborting!");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isGraphLoaded() {
|
||||
return graphInstance != null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void initializeTestGraph() {
|
||||
//nothing to do
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void cleanup() {
|
||||
try {
|
||||
getGraphInstance().close();
|
||||
} catch (Throwable t) {
|
||||
LOG.warn("Could not close test TitanGraph", t);
|
||||
t.printStackTrace();
|
||||
}
|
||||
|
||||
try {
|
||||
TitanCleanup.clear(getGraphInstance());
|
||||
} catch (Throwable t) {
|
||||
LOG.warn("Could not clear test TitanGraph", t);
|
||||
t.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasGraph<Titan1Vertex, Titan1Edge> getGraph() {
|
||||
getGraphInstance();
|
||||
return atlasGraphInstance;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,100 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphIndex;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
import org.apache.tinkerpop.gremlin.structure.Vertex;
|
||||
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
import com.thinkaurelius.titan.core.schema.TitanGraphIndex;
|
||||
|
||||
/**
|
||||
* Represents an Index in Titan 1.
|
||||
*/
|
||||
public class Titan1GraphIndex implements AtlasGraphIndex {
|
||||
|
||||
private TitanGraphIndex wrapped;
|
||||
|
||||
public Titan1GraphIndex(TitanGraphIndex toWrap) {
|
||||
this.wrapped = toWrap;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isEdgeIndex() {
|
||||
return Edge.class.isAssignableFrom(wrapped.getIndexedElement());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isVertexIndex() {
|
||||
return Vertex.class.isAssignableFrom(wrapped.getIndexedElement());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isUnique() {
|
||||
return wrapped.isUnique();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Set<AtlasPropertyKey> getFieldKeys() {
|
||||
PropertyKey[] keys = wrapped.getFieldKeys();
|
||||
Set<AtlasPropertyKey> result = new HashSet<AtlasPropertyKey>();
|
||||
for(PropertyKey key : keys) {
|
||||
result.add(GraphDbObjectFactory.createPropertyKey(key));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = 17;
|
||||
result = 37*result + wrapped.hashCode();
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
if (!(other instanceof Titan1GraphIndex)) {
|
||||
return false;
|
||||
}
|
||||
Titan1GraphIndex otherKey = (Titan1GraphIndex)other;
|
||||
return otherKey.wrapped.equals(wrapped);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isMixedIndex() {
|
||||
return wrapped.isMixedIndex();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean isCompositeIndex() {
|
||||
return wrapped.isCompositeIndex();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,177 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphIndex;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphManagement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
import org.apache.tinkerpop.gremlin.structure.Element;
|
||||
import org.apache.tinkerpop.gremlin.structure.Vertex;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import com.thinkaurelius.titan.core.Cardinality;
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
import com.thinkaurelius.titan.core.schema.Mapping;
|
||||
import com.thinkaurelius.titan.core.schema.PropertyKeyMaker;
|
||||
import com.thinkaurelius.titan.core.schema.TitanGraphIndex;
|
||||
import com.thinkaurelius.titan.core.schema.TitanManagement;
|
||||
import com.thinkaurelius.titan.graphdb.internal.Token;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasGraphManagement.
|
||||
*/
|
||||
public class Titan1GraphManagement implements AtlasGraphManagement {
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(Titan1GraphManagement.class);
|
||||
|
||||
private static final char[] RESERVED_CHARS = { '{', '}', '"', '$', Token.SEPARATOR_CHAR };
|
||||
|
||||
private Titan1Graph graph;
|
||||
private TitanManagement management;
|
||||
|
||||
private Set<String> newMultProperties = new HashSet<>();
|
||||
|
||||
public Titan1GraphManagement(Titan1Graph graph, TitanManagement managementSystem) {
|
||||
this.management = managementSystem;
|
||||
this.graph = graph;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createVertexIndex(String propertyName, String backingIndex, List<AtlasPropertyKey> propertyKeys) {
|
||||
|
||||
TitanManagement.IndexBuilder indexBuilder = management.buildIndex(propertyName, Vertex.class);
|
||||
for (AtlasPropertyKey key : propertyKeys) {
|
||||
PropertyKey titanKey = TitanObjectFactory.createPropertyKey(key);
|
||||
indexBuilder.addKey(titanKey);
|
||||
}
|
||||
indexBuilder.buildMixedIndex(backingIndex);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createEdgeIndex(String index, String backingIndex) {
|
||||
buildMixedIndex(index, Edge.class, backingIndex);
|
||||
}
|
||||
|
||||
private void buildMixedIndex(String index, Class<? extends Element> titanClass, String backingIndex) {
|
||||
|
||||
management.buildIndex(index, titanClass).buildMixedIndex(backingIndex);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createFullTextIndex(String indexName, AtlasPropertyKey propertyKey, String backingIndex) {
|
||||
|
||||
PropertyKey fullText = TitanObjectFactory.createPropertyKey(propertyKey);
|
||||
|
||||
management.buildIndex(indexName, Vertex.class)
|
||||
.addKey(fullText, com.thinkaurelius.titan.core.schema.Parameter.of("mapping", Mapping.TEXT))
|
||||
.buildMixedIndex(backingIndex);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsPropertyKey(String propertyName) {
|
||||
return management.containsPropertyKey(propertyName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void rollback() {
|
||||
management.rollback();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void commit() {
|
||||
graph.addMultiProperties(newMultProperties);
|
||||
newMultProperties.clear();
|
||||
management.commit();
|
||||
}
|
||||
|
||||
private static void checkName(String name) {
|
||||
//for some reason, name checking was removed from StandardPropertyKeyMaker.make()
|
||||
//in titan 1. For consistency, do the check here.
|
||||
Preconditions.checkArgument(StringUtils.isNotBlank(name), "Need to specify name");
|
||||
for (char c : RESERVED_CHARS) {
|
||||
Preconditions.checkArgument(name.indexOf(c) < 0, "Name can not contains reserved character %s: %s", c,
|
||||
name);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasPropertyKey makePropertyKey(String propertyName, Class propertyClass, AtlasCardinality cardinality) {
|
||||
|
||||
if (cardinality.isMany()) {
|
||||
newMultProperties.add(propertyName);
|
||||
}
|
||||
PropertyKeyMaker propertyKeyBuilder = management.makePropertyKey(propertyName).dataType(propertyClass);
|
||||
if (cardinality != null) {
|
||||
Cardinality titanCardinality = TitanObjectFactory.createCardinality(cardinality);
|
||||
propertyKeyBuilder.cardinality(titanCardinality);
|
||||
}
|
||||
PropertyKey propertyKey = propertyKeyBuilder.make();
|
||||
return GraphDbObjectFactory.createPropertyKey(propertyKey);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasPropertyKey getPropertyKey(String propertyName) {
|
||||
checkName(propertyName);
|
||||
return GraphDbObjectFactory.createPropertyKey(management.getPropertyKey(propertyName));
|
||||
}
|
||||
|
||||
public void createExactMatchVertexIndex(String propertyName, boolean enforceUniqueness,
|
||||
List<AtlasPropertyKey> propertyKeys) {
|
||||
|
||||
TitanManagement.IndexBuilder indexBuilder = management.buildIndex(propertyName, Vertex.class);
|
||||
for (AtlasPropertyKey key : propertyKeys) {
|
||||
PropertyKey titanKey = TitanObjectFactory.createPropertyKey(key);
|
||||
indexBuilder.addKey(titanKey);
|
||||
}
|
||||
if (enforceUniqueness) {
|
||||
indexBuilder.unique();
|
||||
}
|
||||
indexBuilder.buildCompositeIndex();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addVertexIndexKey(String indexName, AtlasPropertyKey propertyKey) {
|
||||
PropertyKey titanKey = TitanObjectFactory.createPropertyKey(propertyKey);
|
||||
TitanGraphIndex vertexIndex = management.getGraphIndex(indexName);
|
||||
management.addIndexKey(vertexIndex, titanKey);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasGraphIndex getGraphIndex(String indexName) {
|
||||
TitanGraphIndex index = management.getGraphIndex(indexName);
|
||||
return GraphDbObjectFactory.createGraphIndex(index);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createExactMatchIndex(String propertyName, boolean isUnique,
|
||||
List<AtlasPropertyKey> propertyKeys) {
|
||||
createExactMatchVertexIndex(propertyName, isUnique, propertyKeys);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,79 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.Iterator;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasIndexQuery;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
|
||||
import com.google.common.base.Function;
|
||||
import com.google.common.collect.Iterators;
|
||||
import com.thinkaurelius.titan.core.TitanIndexQuery;
|
||||
import com.thinkaurelius.titan.core.TitanVertex;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasIndexQuery.
|
||||
*/
|
||||
public class Titan1IndexQuery implements AtlasIndexQuery<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
private Titan1Graph graph;
|
||||
private TitanIndexQuery query;
|
||||
|
||||
public Titan1IndexQuery(Titan1Graph graph, TitanIndexQuery query) {
|
||||
this.query = query;
|
||||
this.graph = graph;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterator<Result<Titan1Vertex, Titan1Edge>> vertices() {
|
||||
Iterator<TitanIndexQuery.Result<TitanVertex>> results = query.vertices().iterator();
|
||||
|
||||
Function<TitanIndexQuery.Result<TitanVertex>, Result<Titan1Vertex, Titan1Edge>> function =
|
||||
new Function<TitanIndexQuery.Result<TitanVertex>, Result<Titan1Vertex, Titan1Edge>>() {
|
||||
|
||||
@Override
|
||||
public Result<Titan1Vertex, Titan1Edge> apply(TitanIndexQuery.Result<TitanVertex> source) {
|
||||
return new ResultImpl(source);
|
||||
}
|
||||
};
|
||||
|
||||
return Iterators.transform(results, function);
|
||||
}
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasIndexQuery.Result.
|
||||
*/
|
||||
public final class ResultImpl implements AtlasIndexQuery.Result<Titan1Vertex, Titan1Edge> {
|
||||
private TitanIndexQuery.Result<TitanVertex> source;
|
||||
|
||||
public ResultImpl(TitanIndexQuery.Result<TitanVertex> source) {
|
||||
this.source = source;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertex<Titan1Vertex, Titan1Edge> getVertex() {
|
||||
return GraphDbObjectFactory.createVertex(graph, source.getElement());
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getScore() {
|
||||
return source.getScore();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,77 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public class Titan1PropertyKey implements AtlasPropertyKey {
|
||||
|
||||
private PropertyKey wrapped;
|
||||
|
||||
public Titan1PropertyKey(PropertyKey toWrap) {
|
||||
wrapped = toWrap;
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.apache.atlas.repository.graphdb.AtlasPropertyKey#getName()
|
||||
*/
|
||||
@Override
|
||||
public String getName() {
|
||||
return wrapped.name();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return
|
||||
*/
|
||||
public PropertyKey getWrappedPropertyKey() {
|
||||
return wrapped;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = 17;
|
||||
result = 37*result + wrapped.hashCode();
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
if (!(other instanceof Titan1PropertyKey)) {
|
||||
return false;
|
||||
}
|
||||
Titan1PropertyKey otherKey = (Titan1PropertyKey)other;
|
||||
return otherKey.getWrappedPropertyKey().equals(getWrappedPropertyKey());
|
||||
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.apache.atlas.repository.graphdb.AtlasPropertyKey#getCardinality()
|
||||
*/
|
||||
@Override
|
||||
public AtlasCardinality getCardinality() {
|
||||
return GraphDbObjectFactory.createCardinality(wrapped.cardinality());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,102 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdgeDirection;
|
||||
import org.apache.atlas.repository.graphdb.AtlasSchemaViolationException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertexQuery;
|
||||
import org.apache.tinkerpop.gremlin.structure.Direction;
|
||||
import org.apache.tinkerpop.gremlin.structure.Edge;
|
||||
import org.apache.tinkerpop.gremlin.structure.Vertex;
|
||||
import org.apache.tinkerpop.gremlin.structure.VertexProperty;
|
||||
|
||||
import com.thinkaurelius.titan.core.SchemaViolationException;
|
||||
import com.thinkaurelius.titan.core.TitanVertex;
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasVertex.
|
||||
*/
|
||||
public class Titan1Vertex extends Titan1Element<Vertex> implements AtlasVertex<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
|
||||
public Titan1Vertex(Titan1Graph graph, Vertex source) {
|
||||
super(graph, source);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> void addProperty(String propertyName, T value) {
|
||||
try {
|
||||
getWrappedElement().property(VertexProperty.Cardinality.set, propertyName, value);
|
||||
} catch(SchemaViolationException e) {
|
||||
throw new AtlasSchemaViolationException(e);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> getEdges(AtlasEdgeDirection dir, String edgeLabel) {
|
||||
|
||||
Direction d = TitanObjectFactory.createDirection(dir);
|
||||
Iterator<Edge> edges = getWrappedElement().edges(d, edgeLabel);
|
||||
return graph.wrapEdges(edges);
|
||||
}
|
||||
|
||||
private TitanVertex getAsTitanVertex() {
|
||||
return (TitanVertex)getWrappedElement();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> getEdges(AtlasEdgeDirection in) {
|
||||
Direction d = TitanObjectFactory.createDirection(in);
|
||||
Iterator<Edge> edges = getWrappedElement().edges(d);
|
||||
return graph.wrapEdges(edges);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> Collection<T> getPropertyValues(String propertyName, Class<T> clazz) {
|
||||
|
||||
Collection<T> result = new ArrayList<T>();
|
||||
Iterator<VertexProperty<T>> it = getWrappedElement().properties(propertyName);
|
||||
while(it.hasNext()) {
|
||||
result.add(it.next().value());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertexQuery<Titan1Vertex, Titan1Edge> query() {
|
||||
|
||||
return new Titan1VertexQuery(graph, getAsTitanVertex().query());
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Titan1Vertex getV() {
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,66 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdgeDirection;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertexQuery;
|
||||
|
||||
import com.thinkaurelius.titan.core.TitanVertexQuery;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of AtlasVertexQuery.
|
||||
*/
|
||||
public class Titan1VertexQuery implements AtlasVertexQuery<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
private Titan1Graph graph;
|
||||
private TitanVertexQuery<?> query;
|
||||
|
||||
public Titan1VertexQuery(Titan1Graph graph, TitanVertexQuery<?> query) {
|
||||
this.query = query;
|
||||
this.graph = graph;
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasVertexQuery<Titan1Vertex, Titan1Edge> direction(AtlasEdgeDirection queryDirection) {
|
||||
query.direction(TitanObjectFactory.createDirection(queryDirection));
|
||||
return this;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> vertices() {
|
||||
Iterable vertices = query.vertices();
|
||||
return graph.wrapVertices(vertices);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasEdge<Titan1Vertex, Titan1Edge>> edges() {
|
||||
Iterable edges = query.edges();
|
||||
return graph.wrapEdges(edges);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public long count() {
|
||||
return query.count();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,85 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdgeDirection;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
import org.apache.tinkerpop.gremlin.structure.Direction;
|
||||
|
||||
import com.thinkaurelius.titan.core.Cardinality;
|
||||
import com.thinkaurelius.titan.core.PropertyKey;
|
||||
|
||||
|
||||
/**
|
||||
* Factory that serves up instances of Titan/Tinkerpop classes that correspond to
|
||||
* graph database abstraction layer/Atlas classes.
|
||||
*/
|
||||
public final class TitanObjectFactory {
|
||||
|
||||
private TitanObjectFactory() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves the titan direction corresponding to the given
|
||||
* AtlasEdgeDirection.
|
||||
*
|
||||
* @param dir
|
||||
* @return
|
||||
*/
|
||||
public static Direction createDirection(AtlasEdgeDirection dir) {
|
||||
|
||||
switch(dir) {
|
||||
case IN:
|
||||
return Direction.IN;
|
||||
case OUT:
|
||||
return Direction.OUT;
|
||||
case BOTH:
|
||||
return Direction.BOTH;
|
||||
default:
|
||||
throw new RuntimeException("Unrecognized direction: " + dir);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Converts a Multiplicity to a Cardinality.
|
||||
*
|
||||
* @param multiplicity
|
||||
* @return
|
||||
*/
|
||||
public static Cardinality createCardinality(AtlasCardinality cardinality) {
|
||||
switch(cardinality) {
|
||||
|
||||
case SINGLE:
|
||||
return Cardinality.SINGLE;
|
||||
case LIST:
|
||||
return Cardinality.LIST;
|
||||
case SET:
|
||||
return Cardinality.SET;
|
||||
default:
|
||||
throw new IllegalStateException("Unrecognized cardinality: " + cardinality);
|
||||
}
|
||||
}
|
||||
|
||||
public static PropertyKey createPropertyKey(AtlasPropertyKey key) {
|
||||
return ((Titan1PropertyKey)key).getWrappedPropertyKey();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,136 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.graphson;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Configure how the GraphSON utility treats edge and vertex properties.
|
||||
*
|
||||
* @author Stephen Mallette (http://stephen.genoprime.com)
|
||||
*/
|
||||
public class AtlasElementPropertyConfig {
|
||||
|
||||
/**
|
||||
* Rules for element properties.
|
||||
*/
|
||||
public enum ElementPropertiesRule {
|
||||
INCLUDE, EXCLUDE
|
||||
}
|
||||
|
||||
private final List<String> vertexPropertyKeys;
|
||||
private final List<String> edgePropertyKeys;
|
||||
private final ElementPropertiesRule vertexPropertiesRule;
|
||||
private final ElementPropertiesRule edgePropertiesRule;
|
||||
private final boolean normalized;
|
||||
|
||||
/**
|
||||
* A configuration that includes all properties of vertices and edges.
|
||||
*/
|
||||
public static final AtlasElementPropertyConfig ALL_PROPERTIES = new AtlasElementPropertyConfig(null, null,
|
||||
ElementPropertiesRule.INCLUDE, ElementPropertiesRule.INCLUDE, false);
|
||||
|
||||
public AtlasElementPropertyConfig(final Set<String> vertexPropertyKeys, final Set<String> edgePropertyKeys,
|
||||
final ElementPropertiesRule vertexPropertiesRule, final ElementPropertiesRule edgePropertiesRule) {
|
||||
this(vertexPropertyKeys, edgePropertyKeys, vertexPropertiesRule, edgePropertiesRule, false);
|
||||
}
|
||||
|
||||
public AtlasElementPropertyConfig(final Set<String> vertexPropertyKeys, final Set<String> edgePropertyKeys,
|
||||
final ElementPropertiesRule vertexPropertiesRule, final ElementPropertiesRule edgePropertiesRule,
|
||||
final boolean normalized) {
|
||||
this.vertexPropertiesRule = vertexPropertiesRule;
|
||||
this.vertexPropertyKeys = sortKeys(vertexPropertyKeys, normalized);
|
||||
this.edgePropertiesRule = edgePropertiesRule;
|
||||
this.edgePropertyKeys = sortKeys(edgePropertyKeys, normalized);
|
||||
this.normalized = normalized;
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a configuration that includes the specified properties from
|
||||
* both vertices and edges.
|
||||
*/
|
||||
public static AtlasElementPropertyConfig includeProperties(final Set<String> vertexPropertyKeys,
|
||||
final Set<String> edgePropertyKeys) {
|
||||
return new AtlasElementPropertyConfig(vertexPropertyKeys, edgePropertyKeys, ElementPropertiesRule.INCLUDE,
|
||||
ElementPropertiesRule.INCLUDE);
|
||||
}
|
||||
|
||||
public static AtlasElementPropertyConfig includeProperties(final Set<String> vertexPropertyKeys,
|
||||
final Set<String> edgePropertyKeys,
|
||||
final boolean normalized) {
|
||||
return new AtlasElementPropertyConfig(vertexPropertyKeys, edgePropertyKeys, ElementPropertiesRule.INCLUDE,
|
||||
ElementPropertiesRule.INCLUDE, normalized);
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a configuration that excludes the specified properties from
|
||||
* both vertices and edges.
|
||||
*/
|
||||
public static AtlasElementPropertyConfig excludeProperties(final Set<String> vertexPropertyKeys,
|
||||
final Set<String> edgePropertyKeys) {
|
||||
return new AtlasElementPropertyConfig(vertexPropertyKeys, edgePropertyKeys, ElementPropertiesRule.EXCLUDE,
|
||||
ElementPropertiesRule.EXCLUDE);
|
||||
}
|
||||
|
||||
public static AtlasElementPropertyConfig excludeProperties(final Set<String> vertexPropertyKeys,
|
||||
final Set<String> edgePropertyKeys,
|
||||
final boolean normalized) {
|
||||
return new AtlasElementPropertyConfig(vertexPropertyKeys, edgePropertyKeys, ElementPropertiesRule.EXCLUDE,
|
||||
ElementPropertiesRule.EXCLUDE, normalized);
|
||||
}
|
||||
|
||||
public List<String> getVertexPropertyKeys() {
|
||||
return vertexPropertyKeys;
|
||||
}
|
||||
|
||||
public List<String> getEdgePropertyKeys() {
|
||||
return edgePropertyKeys;
|
||||
}
|
||||
|
||||
public ElementPropertiesRule getVertexPropertiesRule() {
|
||||
return vertexPropertiesRule;
|
||||
}
|
||||
|
||||
public ElementPropertiesRule getEdgePropertiesRule() {
|
||||
return edgePropertiesRule;
|
||||
}
|
||||
|
||||
public boolean isNormalized() {
|
||||
return normalized;
|
||||
}
|
||||
|
||||
private static List<String> sortKeys(final Set<String> keys, final boolean normalized) {
|
||||
final List<String> propertyKeyList;
|
||||
if (keys != null) {
|
||||
if (normalized) {
|
||||
final List<String> sorted = new ArrayList<String>(keys);
|
||||
Collections.sort(sorted);
|
||||
propertyKeyList = sorted;
|
||||
} else {
|
||||
propertyKeyList = new ArrayList<String>(keys);
|
||||
}
|
||||
} else {
|
||||
propertyKeyList = null;
|
||||
}
|
||||
|
||||
return propertyKeyList;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.graphson;
|
||||
|
||||
/**
|
||||
* Modes of operation of the GraphSONUtility.
|
||||
*
|
||||
* @author Stephen Mallette
|
||||
*/
|
||||
public enum AtlasGraphSONMode {
|
||||
/**
|
||||
* COMPACT constructs GraphSON on the assumption that all property keys
|
||||
* are fair game for exclusion including _type, _inV, _outV, _label and _id.
|
||||
* It is possible to write GraphSON that cannot be read back into Graph,
|
||||
* if some or all of these keys are excluded.
|
||||
*/
|
||||
COMPACT,
|
||||
|
||||
/**
|
||||
* NORMAL includes the _type field and JSON data typing.
|
||||
*/
|
||||
NORMAL,
|
||||
|
||||
/**
|
||||
* EXTENDED includes the _type field and explicit data typing.
|
||||
*/
|
||||
EXTENDED
|
||||
}
|
||||
|
|
@ -0,0 +1,51 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.graphson;
|
||||
|
||||
/**
|
||||
* @author Stephen Mallette (http://stephen.genoprime.com)
|
||||
*/
|
||||
public final class AtlasGraphSONTokens {
|
||||
|
||||
private AtlasGraphSONTokens() {}
|
||||
|
||||
public static final String VERTEX = "vertex";
|
||||
public static final String EDGE = "edge";
|
||||
public static final String INTERNAL_ID = "_id";
|
||||
public static final String INTERNAL_LABEL = "_label";
|
||||
public static final String INTERNAL_TYPE = "_type";
|
||||
public static final String INTERNAL_OUT_V = "_outV";
|
||||
public static final String INTERNAL_IN_V = "_inV";
|
||||
public static final String VALUE = "value";
|
||||
public static final String TYPE = "type";
|
||||
public static final String TYPE_LIST = "list";
|
||||
public static final String TYPE_STRING = "string";
|
||||
public static final String TYPE_DOUBLE = "double";
|
||||
public static final String TYPE_INTEGER = "integer";
|
||||
public static final String TYPE_FLOAT = "float";
|
||||
public static final String TYPE_MAP = "map";
|
||||
public static final String TYPE_BOOLEAN = "boolean";
|
||||
public static final String TYPE_LONG = "long";
|
||||
public static final String TYPE_SHORT = "short";
|
||||
public static final String TYPE_BYTE = "byte";
|
||||
public static final String TYPE_UNKNOWN = "unknown";
|
||||
|
||||
public static final String VERTICES = "vertices";
|
||||
public static final String EDGES = "edges";
|
||||
public static final String MODE = "mode";
|
||||
}
|
||||
|
|
@ -0,0 +1,513 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.graphson;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Array;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasElement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.titan1.graphson.AtlasElementPropertyConfig.ElementPropertiesRule;
|
||||
import org.codehaus.jettison.json.JSONException;
|
||||
import org.codehaus.jettison.json.JSONObject;
|
||||
import org.codehaus.jettison.json.JSONTokener;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.node.ArrayNode;
|
||||
import com.fasterxml.jackson.databind.node.JsonNodeFactory;
|
||||
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||
|
||||
/**
|
||||
* This class was largely removed from tinkerpop 1. We're adding it back here to
|
||||
* avoid changing the format of the JSON that we produce.
|
||||
*
|
||||
* Helps write individual graph elements to TinkerPop JSON format known as
|
||||
* GraphSON.
|
||||
*
|
||||
* @author Stephen Mallette (http://stephen.genoprime.com)
|
||||
*/
|
||||
public final class AtlasGraphSONUtility {
|
||||
|
||||
private static final JsonNodeFactory JSON_NODE_FACTORY = JsonNodeFactory.instance;
|
||||
|
||||
private static final ObjectMapper MAPPER = new ObjectMapper();
|
||||
|
||||
private final AtlasGraphSONMode mode;
|
||||
private final List<String> vertexPropertyKeys;
|
||||
private final List<String> edgePropertyKeys;
|
||||
|
||||
private final ElementPropertiesRule vertexPropertiesRule;
|
||||
private final ElementPropertiesRule edgePropertiesRule;
|
||||
private final boolean normalized;
|
||||
|
||||
private final boolean includeReservedVertexId;
|
||||
private final boolean includeReservedEdgeId;
|
||||
private final boolean includeReservedVertexType;
|
||||
private final boolean includeReservedEdgeType;
|
||||
private final boolean includeReservedEdgeLabel;
|
||||
private final boolean includeReservedEdgeOutV;
|
||||
private final boolean includeReservedEdgeInV;
|
||||
|
||||
/**
|
||||
* A GraphSONUtility that includes the specified properties.
|
||||
*/
|
||||
private AtlasGraphSONUtility(final AtlasGraphSONMode mode, final Set<String> vertexPropertyKeySet,
|
||||
final Set<String> edgePropertyKeySet) {
|
||||
|
||||
AtlasElementPropertyConfig config = AtlasElementPropertyConfig.includeProperties(vertexPropertyKeySet,
|
||||
edgePropertyKeySet);
|
||||
|
||||
this.vertexPropertyKeys = config.getVertexPropertyKeys();
|
||||
this.edgePropertyKeys = config.getEdgePropertyKeys();
|
||||
this.vertexPropertiesRule = config.getVertexPropertiesRule();
|
||||
this.edgePropertiesRule = config.getEdgePropertiesRule();
|
||||
this.normalized = config.isNormalized();
|
||||
|
||||
this.mode = mode;
|
||||
|
||||
this.includeReservedVertexId = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_ID, vertexPropertyKeys,
|
||||
this.vertexPropertiesRule);
|
||||
this.includeReservedEdgeId = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_ID, edgePropertyKeys,
|
||||
this.edgePropertiesRule);
|
||||
this.includeReservedVertexType = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_TYPE, vertexPropertyKeys,
|
||||
this.vertexPropertiesRule);
|
||||
this.includeReservedEdgeType = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_TYPE, edgePropertyKeys,
|
||||
this.edgePropertiesRule);
|
||||
this.includeReservedEdgeLabel = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_LABEL, edgePropertyKeys,
|
||||
this.edgePropertiesRule);
|
||||
this.includeReservedEdgeOutV = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_OUT_V, edgePropertyKeys,
|
||||
this.edgePropertiesRule);
|
||||
this.includeReservedEdgeInV = includeReservedKey(mode, AtlasGraphSONTokens.INTERNAL_IN_V, edgePropertyKeys,
|
||||
this.edgePropertiesRule);
|
||||
}
|
||||
|
||||
/*
|
||||
* Creates GraphSON for a single graph element.
|
||||
*/
|
||||
private JSONObject jsonFromElement(final AtlasElement element) throws JSONException {
|
||||
final ObjectNode objectNode = this.objectNodeFromElement(element);
|
||||
|
||||
try {
|
||||
return new JSONObject(new JSONTokener(MAPPER.writeValueAsString(objectNode)));
|
||||
} catch (IOException ioe) {
|
||||
// repackage this as a JSONException...seems sensible as the caller will only know about
|
||||
// the jettison object not being created
|
||||
throw new JSONException(ioe);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates GraphSON for a single graph element.
|
||||
*/
|
||||
private ObjectNode objectNodeFromElement(final AtlasElement element) {
|
||||
final boolean isEdge = element instanceof AtlasEdge;
|
||||
final boolean showTypes = mode == AtlasGraphSONMode.EXTENDED;
|
||||
final List<String> propertyKeys = isEdge ? this.edgePropertyKeys : this.vertexPropertyKeys;
|
||||
final ElementPropertiesRule elementPropertyConfig = isEdge ? this.edgePropertiesRule
|
||||
: this.vertexPropertiesRule;
|
||||
|
||||
final ObjectNode jsonElement = createJSONMap(
|
||||
createPropertyMap(element, propertyKeys, elementPropertyConfig, normalized), propertyKeys, showTypes);
|
||||
|
||||
if ((isEdge && this.includeReservedEdgeId) || (!isEdge && this.includeReservedVertexId)) {
|
||||
putObject(jsonElement, AtlasGraphSONTokens.INTERNAL_ID, element.getId());
|
||||
}
|
||||
|
||||
// it's important to keep the order of these straight. check AtlasEdge first and then AtlasVertex because there
|
||||
// are graph implementations that have AtlasEdge extend from AtlasVertex
|
||||
if (element instanceof AtlasEdge) {
|
||||
final AtlasEdge edge = (AtlasEdge) element;
|
||||
|
||||
if (this.includeReservedEdgeId) {
|
||||
putObject(jsonElement, AtlasGraphSONTokens.INTERNAL_ID, element.getId());
|
||||
}
|
||||
|
||||
if (this.includeReservedEdgeType) {
|
||||
jsonElement.put(AtlasGraphSONTokens.INTERNAL_TYPE, AtlasGraphSONTokens.EDGE);
|
||||
}
|
||||
|
||||
if (this.includeReservedEdgeOutV) {
|
||||
putObject(jsonElement, AtlasGraphSONTokens.INTERNAL_OUT_V, edge.getOutVertex().getId());
|
||||
}
|
||||
|
||||
if (this.includeReservedEdgeInV) {
|
||||
putObject(jsonElement, AtlasGraphSONTokens.INTERNAL_IN_V, edge.getInVertex().getId());
|
||||
}
|
||||
|
||||
if (this.includeReservedEdgeLabel) {
|
||||
jsonElement.put(AtlasGraphSONTokens.INTERNAL_LABEL, edge.getLabel());
|
||||
}
|
||||
} else if (element instanceof AtlasVertex) {
|
||||
if (this.includeReservedVertexId) {
|
||||
putObject(jsonElement, AtlasGraphSONTokens.INTERNAL_ID, element.getId());
|
||||
}
|
||||
|
||||
if (this.includeReservedVertexType) {
|
||||
jsonElement.put(AtlasGraphSONTokens.INTERNAL_TYPE, AtlasGraphSONTokens.VERTEX);
|
||||
}
|
||||
}
|
||||
|
||||
return jsonElement;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a Jettison JSONObject from a graph element.
|
||||
*
|
||||
* @param element
|
||||
* the graph element to convert to JSON.
|
||||
* @param propertyKeys
|
||||
* The property getPropertyKeys() at the root of the element to
|
||||
* serialize. If null, then all getPropertyKeys() are serialized.
|
||||
* @param mode
|
||||
* the type of GraphSON to be generated.
|
||||
*/
|
||||
public static JSONObject jsonFromElement(final AtlasElement element, final Set<String> propertyKeys,
|
||||
final AtlasGraphSONMode mode)
|
||||
throws JSONException {
|
||||
|
||||
final AtlasGraphSONUtility graphson = element instanceof AtlasEdge
|
||||
? new AtlasGraphSONUtility(mode, null, propertyKeys)
|
||||
: new AtlasGraphSONUtility(mode, propertyKeys, null);
|
||||
return graphson.jsonFromElement(element);
|
||||
}
|
||||
|
||||
private static ObjectNode objectNodeFromElement(final AtlasElement element, final List<String> propertyKeys,
|
||||
final AtlasGraphSONMode mode) {
|
||||
final AtlasGraphSONUtility graphson = element instanceof AtlasEdge
|
||||
? new AtlasGraphSONUtility(mode, null, new HashSet<String>(propertyKeys))
|
||||
: new AtlasGraphSONUtility(mode, new HashSet<String>(propertyKeys), null);
|
||||
return graphson.objectNodeFromElement(element);
|
||||
}
|
||||
|
||||
private static boolean includeReservedKey(final AtlasGraphSONMode mode, final String key,
|
||||
final List<String> propertyKeys, final ElementPropertiesRule rule) {
|
||||
// the key is always included in modes other than compact. if it is compact, then validate that the
|
||||
// key is in the property key list
|
||||
return mode != AtlasGraphSONMode.COMPACT || includeKey(key, propertyKeys, rule);
|
||||
}
|
||||
|
||||
private static boolean includeKey(final String key, final List<String> propertyKeys,
|
||||
final ElementPropertiesRule rule) {
|
||||
if (propertyKeys == null) {
|
||||
// when null always include the key and shortcut this piece
|
||||
return true;
|
||||
}
|
||||
|
||||
// default the key situation. if it's included then it should be explicitly defined in the
|
||||
// property getPropertyKeys() list to be included or the reverse otherwise
|
||||
boolean keySituation = rule == ElementPropertiesRule.INCLUDE;
|
||||
|
||||
switch (rule) {
|
||||
case INCLUDE:
|
||||
keySituation = propertyKeys.contains(key);
|
||||
break;
|
||||
case EXCLUDE:
|
||||
keySituation = !propertyKeys.contains(key);
|
||||
break;
|
||||
default:
|
||||
throw new RuntimeException("Unhandled rule: " + rule);
|
||||
}
|
||||
|
||||
return keySituation;
|
||||
}
|
||||
|
||||
private static ArrayNode createJSONList(final List<Object> list, final List<String> propertyKeys,
|
||||
final boolean showTypes) {
|
||||
final ArrayNode jsonList = JSON_NODE_FACTORY.arrayNode();
|
||||
for (Object item : list) {
|
||||
if (item instanceof AtlasElement) {
|
||||
jsonList.add(objectNodeFromElement((AtlasElement) item, propertyKeys,
|
||||
showTypes ? AtlasGraphSONMode.EXTENDED : AtlasGraphSONMode.NORMAL));
|
||||
} else if (item instanceof List) {
|
||||
jsonList.add(createJSONList((List<Object>) item, propertyKeys, showTypes));
|
||||
} else if (item instanceof Map) {
|
||||
jsonList.add(createJSONMap((Map<String, Object>) item, propertyKeys, showTypes));
|
||||
} else if (item != null && item.getClass().isArray()) {
|
||||
jsonList.add(createJSONList(convertArrayToList(item), propertyKeys, showTypes));
|
||||
} else {
|
||||
addObject(jsonList, item);
|
||||
}
|
||||
}
|
||||
return jsonList;
|
||||
}
|
||||
|
||||
private static ObjectNode createJSONMap(final Map<String, Object> map, final List<String> propertyKeys,
|
||||
final boolean showTypes) {
|
||||
final ObjectNode jsonMap = JSON_NODE_FACTORY.objectNode();
|
||||
for (Object key : map.keySet()) {
|
||||
Object value = map.get(key);
|
||||
if (value != null) {
|
||||
if (value instanceof List) {
|
||||
value = createJSONList((List<Object>) value, propertyKeys, showTypes);
|
||||
} else if (value instanceof Map) {
|
||||
value = createJSONMap((Map<String, Object>) value, propertyKeys, showTypes);
|
||||
} else if (value instanceof AtlasElement) {
|
||||
value = objectNodeFromElement((AtlasElement) value, propertyKeys,
|
||||
showTypes ? AtlasGraphSONMode.EXTENDED : AtlasGraphSONMode.NORMAL);
|
||||
} else if (value.getClass().isArray()) {
|
||||
value = createJSONList(convertArrayToList(value), propertyKeys, showTypes);
|
||||
}
|
||||
}
|
||||
|
||||
putObject(jsonMap, key.toString(), getValue(value, showTypes));
|
||||
}
|
||||
return jsonMap;
|
||||
|
||||
}
|
||||
|
||||
private static void addObject(final ArrayNode jsonList, final Object value) {
|
||||
if (value == null) {
|
||||
jsonList.add((JsonNode) null);
|
||||
} else if (value.getClass() == Boolean.class) {
|
||||
jsonList.add((Boolean) value);
|
||||
} else if (value.getClass() == Long.class) {
|
||||
jsonList.add((Long) value);
|
||||
} else if (value.getClass() == Integer.class) {
|
||||
jsonList.add((Integer) value);
|
||||
} else if (value.getClass() == Float.class) {
|
||||
jsonList.add((Float) value);
|
||||
} else if (value.getClass() == Double.class) {
|
||||
jsonList.add((Double) value);
|
||||
} else if (value.getClass() == Byte.class) {
|
||||
jsonList.add((Byte) value);
|
||||
} else if (value.getClass() == Short.class) {
|
||||
jsonList.add((Short) value);
|
||||
} else if (value.getClass() == String.class) {
|
||||
jsonList.add((String) value);
|
||||
} else if (value instanceof ObjectNode) {
|
||||
jsonList.add((ObjectNode) value);
|
||||
} else if (value instanceof ArrayNode) {
|
||||
jsonList.add((ArrayNode) value);
|
||||
} else {
|
||||
jsonList.add(value.toString());
|
||||
}
|
||||
}
|
||||
|
||||
private static void putObject(final ObjectNode jsonMap, final String key, final Object value) {
|
||||
if (value == null) {
|
||||
jsonMap.put(key, (JsonNode) null);
|
||||
} else if (value.getClass() == Boolean.class) {
|
||||
jsonMap.put(key, (Boolean) value);
|
||||
} else if (value.getClass() == Long.class) {
|
||||
jsonMap.put(key, (Long) value);
|
||||
} else if (value.getClass() == Integer.class) {
|
||||
jsonMap.put(key, (Integer) value);
|
||||
} else if (value.getClass() == Float.class) {
|
||||
jsonMap.put(key, (Float) value);
|
||||
} else if (value.getClass() == Double.class) {
|
||||
jsonMap.put(key, (Double) value);
|
||||
} else if (value.getClass() == Short.class) {
|
||||
jsonMap.put(key, (Short) value);
|
||||
} else if (value.getClass() == Byte.class) {
|
||||
jsonMap.put(key, (Byte) value);
|
||||
} else if (value.getClass() == String.class) {
|
||||
jsonMap.put(key, (String) value);
|
||||
} else if (value instanceof ObjectNode) {
|
||||
jsonMap.put(key, (ObjectNode) value);
|
||||
} else if (value instanceof ArrayNode) {
|
||||
jsonMap.put(key, (ArrayNode) value);
|
||||
} else {
|
||||
jsonMap.put(key, value.toString());
|
||||
}
|
||||
}
|
||||
|
||||
private static Map<String, Object> createPropertyMap(final AtlasElement element, final List<String> propertyKeys,
|
||||
final ElementPropertiesRule rule, final boolean normalized) {
|
||||
final Map<String, Object> map = new HashMap<String, Object>();
|
||||
final List<String> propertyKeyList;
|
||||
if (normalized) {
|
||||
final List<String> sorted = new ArrayList<String>(element.getPropertyKeys());
|
||||
Collections.sort(sorted);
|
||||
propertyKeyList = sorted;
|
||||
} else {
|
||||
propertyKeyList = new ArrayList<String>(element.getPropertyKeys());
|
||||
}
|
||||
|
||||
if (propertyKeys == null) {
|
||||
for (String key : propertyKeyList) {
|
||||
final Object valToPutInMap = element.getProperty(key, Object.class);
|
||||
if (valToPutInMap != null) {
|
||||
map.put(key, valToPutInMap);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (rule == ElementPropertiesRule.INCLUDE) {
|
||||
for (String key : propertyKeys) {
|
||||
final Object valToPutInMap = element.getProperty(key, Object.class);
|
||||
if (valToPutInMap != null) {
|
||||
map.put(key, valToPutInMap);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (String key : propertyKeyList) {
|
||||
if (!propertyKeys.contains(key)) {
|
||||
final Object valToPutInMap = element.getProperty(key, Object.class);
|
||||
if (valToPutInMap != null) {
|
||||
map.put(key, valToPutInMap);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return map;
|
||||
}
|
||||
|
||||
private static Object getValue(Object value, final boolean includeType) {
|
||||
|
||||
Object returnValue = value;
|
||||
|
||||
// if the includeType is set to true then show the data types of the properties
|
||||
if (includeType) {
|
||||
|
||||
// type will be one of: map, list, string, long, int, double, float.
|
||||
// in the event of a complex object it will call a toString and store as a
|
||||
// string
|
||||
String type = determineType(value);
|
||||
|
||||
ObjectNode valueAndType = JSON_NODE_FACTORY.objectNode();
|
||||
valueAndType.put(AtlasGraphSONTokens.TYPE, type);
|
||||
|
||||
if (type.equals(AtlasGraphSONTokens.TYPE_LIST)) {
|
||||
|
||||
// values of lists must be accumulated as ObjectNode objects under the value key.
|
||||
// will return as a ArrayNode. called recursively to traverse the entire
|
||||
// object graph of each item in the array.
|
||||
ArrayNode list = (ArrayNode) value;
|
||||
|
||||
// there is a set of values that must be accumulated as an array under a key
|
||||
ArrayNode valueArray = valueAndType.putArray(AtlasGraphSONTokens.VALUE);
|
||||
for (int ix = 0; ix < list.size(); ix++) {
|
||||
// the value of each item in the array is a node object from an ArrayNode...must
|
||||
// get the value of it.
|
||||
addObject(valueArray, getValue(getTypedValueFromJsonNode(list.get(ix)), includeType));
|
||||
}
|
||||
|
||||
} else if (type.equals(AtlasGraphSONTokens.TYPE_MAP)) {
|
||||
|
||||
// maps are converted to a ObjectNode. called recursively to traverse
|
||||
// the entire object graph within the map.
|
||||
ObjectNode convertedMap = JSON_NODE_FACTORY.objectNode();
|
||||
ObjectNode jsonObject = (ObjectNode) value;
|
||||
Iterator<?> keyIterator = jsonObject.fieldNames();
|
||||
while (keyIterator.hasNext()) {
|
||||
Object key = keyIterator.next();
|
||||
|
||||
// no need to getValue() here as this is already a ObjectNode and should have type info
|
||||
convertedMap.put(key.toString(), jsonObject.get(key.toString()));
|
||||
}
|
||||
|
||||
valueAndType.put(AtlasGraphSONTokens.VALUE, convertedMap);
|
||||
} else {
|
||||
|
||||
// this must be a primitive value or a complex object. if a complex
|
||||
// object it will be handled by a call to toString and stored as a
|
||||
// string value
|
||||
putObject(valueAndType, AtlasGraphSONTokens.VALUE, value);
|
||||
}
|
||||
|
||||
// this goes back as a JSONObject with data type and value
|
||||
returnValue = valueAndType;
|
||||
}
|
||||
|
||||
return returnValue;
|
||||
}
|
||||
|
||||
private static Object getTypedValueFromJsonNode(JsonNode node) {
|
||||
Object theValue = null;
|
||||
|
||||
if (node != null && !node.isNull()) {
|
||||
if (node.isBoolean()) {
|
||||
theValue = node.booleanValue();
|
||||
} else if (node.isDouble()) {
|
||||
theValue = node.doubleValue();
|
||||
} else if (node.isFloatingPointNumber()) {
|
||||
theValue = node.floatValue();
|
||||
} else if (node.isInt()) {
|
||||
theValue = node.intValue();
|
||||
} else if (node.isLong()) {
|
||||
theValue = node.longValue();
|
||||
} else if (node.isTextual()) {
|
||||
theValue = node.textValue();
|
||||
} else if (node.isArray()) {
|
||||
// this is an array so just send it back so that it can be
|
||||
// reprocessed to its primitive components
|
||||
theValue = node;
|
||||
} else if (node.isObject()) {
|
||||
// this is an object so just send it back so that it can be
|
||||
// reprocessed to its primitive components
|
||||
theValue = node;
|
||||
} else {
|
||||
theValue = node.textValue();
|
||||
}
|
||||
}
|
||||
|
||||
return theValue;
|
||||
}
|
||||
|
||||
private static List<Object> convertArrayToList(final Object value) {
|
||||
final ArrayList<Object> list = new ArrayList<Object>();
|
||||
int arrlength = Array.getLength(value);
|
||||
for (int i = 0; i < arrlength; i++) {
|
||||
Object object = Array.get(value, i);
|
||||
list.add(object);
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
private static String determineType(final Object value) {
|
||||
String type = AtlasGraphSONTokens.TYPE_STRING;
|
||||
if (value == null) {
|
||||
type = AtlasGraphSONTokens.TYPE_UNKNOWN;
|
||||
} else if (value.getClass() == Double.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_DOUBLE;
|
||||
} else if (value.getClass() == Float.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_FLOAT;
|
||||
} else if (value.getClass() == Byte.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_BYTE;
|
||||
} else if (value.getClass() == Short.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_SHORT;
|
||||
} else if (value.getClass() == Integer.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_INTEGER;
|
||||
} else if (value.getClass() == Long.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_LONG;
|
||||
} else if (value.getClass() == Boolean.class) {
|
||||
type = AtlasGraphSONTokens.TYPE_BOOLEAN;
|
||||
} else if (value instanceof ArrayNode) {
|
||||
type = AtlasGraphSONTokens.TYPE_LIST;
|
||||
} else if (value instanceof ObjectNode) {
|
||||
type = AtlasGraphSONTokens.TYPE_MAP;
|
||||
}
|
||||
|
||||
return type;
|
||||
}
|
||||
|
||||
static class ElementFactory {
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,85 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.query;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery.ComparisionOperator;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.repository.graphdb.titan.query.NativeTitanGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Edge;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Graph;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1GraphDatabase;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Vertex;
|
||||
import org.apache.tinkerpop.gremlin.process.traversal.Compare;
|
||||
|
||||
import com.thinkaurelius.titan.core.TitanGraphQuery;
|
||||
import com.thinkaurelius.titan.core.TitanVertex;
|
||||
import com.thinkaurelius.titan.core.attribute.Contain;
|
||||
import com.thinkaurelius.titan.graphdb.query.TitanPredicate;
|
||||
|
||||
/**
|
||||
* Titan 1.0.0 implementation of NativeTitanGraphQuery.
|
||||
*/
|
||||
public class NativeTitan1GraphQuery implements NativeTitanGraphQuery<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
private Titan1Graph graph;
|
||||
private TitanGraphQuery<?> query;
|
||||
|
||||
public NativeTitan1GraphQuery(Titan1Graph graph) {
|
||||
this.query = Titan1GraphDatabase.getGraphInstance().query();
|
||||
this.graph = graph;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterable<AtlasVertex<Titan1Vertex, Titan1Edge>> vertices() {
|
||||
Iterable<TitanVertex> it = query.vertices();
|
||||
return graph.wrapVertices(it);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void in(String propertyName, Collection<? extends Object> values) {
|
||||
query.has(propertyName, Contain.IN, values);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void has(String propertyName, ComparisionOperator op, Object value) {
|
||||
|
||||
Compare c = getGremlinPredicate(op);
|
||||
TitanPredicate pred = TitanPredicate.Converter.convert(c);
|
||||
query.has(propertyName, pred, value);
|
||||
}
|
||||
|
||||
private Compare getGremlinPredicate(ComparisionOperator op) {
|
||||
switch (op) {
|
||||
case EQUAL:
|
||||
return Compare.eq;
|
||||
case GREATER_THAN_EQUAL:
|
||||
return Compare.gte;
|
||||
case LESS_THAN_EQUAL:
|
||||
return Compare.lte;
|
||||
case NOT_EQUAL:
|
||||
return Compare.neq;
|
||||
|
||||
default:
|
||||
throw new RuntimeException("Unsupported comparison operator:" + op);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,55 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.query;
|
||||
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.titan.query.TitanGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.titan.query.NativeTitanGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.titan.query.NativeTitanQueryFactory;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Edge;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Graph;
|
||||
import org.apache.atlas.repository.graphdb.titan1.Titan1Vertex;
|
||||
/**
|
||||
* Titan 1.0.0 implementation of TitanGraphQuery.
|
||||
*/
|
||||
public class Titan1GraphQuery extends TitanGraphQuery<Titan1Vertex, Titan1Edge>
|
||||
implements NativeTitanQueryFactory<Titan1Vertex, Titan1Edge> {
|
||||
|
||||
public Titan1GraphQuery(Titan1Graph graph, boolean isChildQuery) {
|
||||
super(graph, isChildQuery);
|
||||
}
|
||||
|
||||
public Titan1GraphQuery(Titan1Graph graph) {
|
||||
super(graph);
|
||||
}
|
||||
|
||||
@Override
|
||||
public AtlasGraphQuery<Titan1Vertex, Titan1Edge> createChildQuery() {
|
||||
return new Titan1GraphQuery((Titan1Graph) graph, true);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected NativeTitanQueryFactory<Titan1Vertex, Titan1Edge> getQueryFactory() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public NativeTitanGraphQuery<Titan1Vertex, Titan1Edge> createNativeTitanQuery() {
|
||||
return new NativeTitan1GraphQuery((Titan1Graph) graph);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,48 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.serializer;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.math.BigInteger;
|
||||
|
||||
import com.thinkaurelius.titan.core.attribute.AttributeSerializer;
|
||||
import com.thinkaurelius.titan.diskstorage.ScanBuffer;
|
||||
import com.thinkaurelius.titan.diskstorage.WriteBuffer;
|
||||
/**
|
||||
* Serializer for BigDecimal values.
|
||||
*/
|
||||
public class BigDecimalSerializer implements AttributeSerializer<BigDecimal> {
|
||||
|
||||
private final BigIntegerSerializer bigIntegerDelegate = new BigIntegerSerializer();
|
||||
|
||||
@Override
|
||||
public BigDecimal read(ScanBuffer buffer) {
|
||||
BigInteger unscaledVal = bigIntegerDelegate.read(buffer);
|
||||
int scale = buffer.getInt();
|
||||
return new BigDecimal(unscaledVal, scale);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(WriteBuffer buffer, BigDecimal attribute) {
|
||||
BigInteger unscaledVal = attribute.unscaledValue();
|
||||
int scale = attribute.scale();
|
||||
bigIntegerDelegate.write(buffer, unscaledVal);
|
||||
buffer.putInt(scale);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.serializer;
|
||||
|
||||
import java.math.BigInteger;
|
||||
|
||||
import com.thinkaurelius.titan.core.attribute.AttributeSerializer;
|
||||
import com.thinkaurelius.titan.diskstorage.ScanBuffer;
|
||||
import com.thinkaurelius.titan.diskstorage.WriteBuffer;
|
||||
import com.thinkaurelius.titan.graphdb.database.serialize.attribute.ByteArraySerializer;
|
||||
|
||||
/**
|
||||
* Serializer for BigInteger values.
|
||||
*/
|
||||
public class BigIntegerSerializer implements AttributeSerializer<BigInteger> {
|
||||
|
||||
private final ByteArraySerializer delegate = new ByteArraySerializer();
|
||||
|
||||
@Override
|
||||
public BigInteger read(ScanBuffer buffer) {
|
||||
byte[] value = delegate.read(buffer);
|
||||
return new BigInteger(value);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(WriteBuffer buffer, BigInteger attribute) {
|
||||
byte[] value = attribute.toByteArray();
|
||||
delegate.write(buffer, value);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,53 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.serializer;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import com.thinkaurelius.titan.core.attribute.AttributeSerializer;
|
||||
import com.thinkaurelius.titan.diskstorage.ScanBuffer;
|
||||
import com.thinkaurelius.titan.diskstorage.WriteBuffer;
|
||||
import com.thinkaurelius.titan.graphdb.database.idhandling.VariableLong;
|
||||
import com.thinkaurelius.titan.graphdb.database.serialize.attribute.StringSerializer;
|
||||
/**
|
||||
* Serializer for String lists.
|
||||
*/
|
||||
public class StringListSerializer implements AttributeSerializer<List<String>> {
|
||||
|
||||
private final StringSerializer stringSerializer = new StringSerializer();
|
||||
|
||||
@Override
|
||||
public List<String> read(ScanBuffer buffer) {
|
||||
int length = (int)VariableLong.readPositive(buffer);
|
||||
List<String> result = new ArrayList<String>(length);
|
||||
for(int i = 0; i < length; i++) {
|
||||
result.add(stringSerializer.read(buffer));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void write(WriteBuffer buffer, List<String> attributes) {
|
||||
VariableLong.writePositive(buffer, attributes.size());
|
||||
for(String attr : attributes) {
|
||||
stringSerializer.write(buffer, attr);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,31 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1.serializer;
|
||||
|
||||
import org.apache.atlas.typesystem.types.DataTypes.TypeCategory;
|
||||
|
||||
import com.thinkaurelius.titan.graphdb.database.serialize.attribute.EnumSerializer;
|
||||
|
||||
/**
|
||||
* Serializer for TypeCategory value.
|
||||
*/
|
||||
public class TypeCategorySerializer extends EnumSerializer<TypeCategory> {
|
||||
public TypeCategorySerializer() {
|
||||
super(TypeCategory.class);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
org.apache.tinkerpop.gremlin.groovy.jsr223.GremlinGroovyScriptEngineFactory
|
||||
|
|
@ -0,0 +1,191 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
import org.apache.atlas.repository.Constants;
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphManagement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.testng.annotations.AfterClass;
|
||||
import org.testng.annotations.AfterMethod;
|
||||
import org.testng.annotations.BeforeClass;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
public abstract class AbstractGraphDatabaseTest {
|
||||
|
||||
protected static final String WEIGHT_PROPERTY = "weight";
|
||||
protected static final String TRAIT_NAMES = Constants.TRAIT_NAMES_PROPERTY_KEY;
|
||||
protected static final String TYPE_PROPERTY_NAME = "__type";
|
||||
protected static final String TYPESYSTEM = "TYPESYSTEM";
|
||||
|
||||
private static final String BACKING_INDEX_NAME = "backing";
|
||||
|
||||
private AtlasGraph<?, ?> graph = null;
|
||||
|
||||
|
||||
public AbstractGraphDatabaseTest() {
|
||||
super();
|
||||
}
|
||||
|
||||
@BeforeClass
|
||||
public static void createIndices() {
|
||||
Titan1GraphDatabase db = new Titan1GraphDatabase();
|
||||
AtlasGraphManagement mgmt = db.getGraph().getManagementSystem();
|
||||
|
||||
if (mgmt.getGraphIndex(BACKING_INDEX_NAME) == null) {
|
||||
mgmt.createVertexIndex(BACKING_INDEX_NAME, Constants.BACKING_INDEX,
|
||||
Collections.<AtlasPropertyKey>emptyList());
|
||||
}
|
||||
mgmt.makePropertyKey("age13", Integer.class, AtlasCardinality.SINGLE);
|
||||
|
||||
createIndices(mgmt, "name", String.class, false, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, WEIGHT_PROPERTY, Integer.class, false, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, "size15", String.class, false, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, "typeName", String.class, false, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, "__type", String.class, false, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, Constants.GUID_PROPERTY_KEY, String.class, true, AtlasCardinality.SINGLE);
|
||||
createIndices(mgmt, Constants.TRAIT_NAMES_PROPERTY_KEY, String.class, false, AtlasCardinality.SET);
|
||||
createIndices(mgmt, Constants.SUPER_TYPES_PROPERTY_KEY, String.class, false, AtlasCardinality.SET);
|
||||
mgmt.commit();
|
||||
}
|
||||
|
||||
@AfterMethod
|
||||
public void commitGraph() {
|
||||
//force any pending actions to be committed so we can be sure they don't cause errors.
|
||||
pushChangesAndFlushCache();
|
||||
getGraph().commit();
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public static void cleanUp() {
|
||||
Titan1Graph graph = new Titan1Graph();
|
||||
graph.clear();
|
||||
|
||||
}
|
||||
|
||||
protected <V, E> void pushChangesAndFlushCache() {
|
||||
getGraph().commit();
|
||||
}
|
||||
|
||||
private static void createIndices(AtlasGraphManagement management, String propertyName, Class propertyClass,
|
||||
boolean isUnique, AtlasCardinality cardinality) {
|
||||
|
||||
if (management.containsPropertyKey(propertyName)) {
|
||||
//index was already created
|
||||
return;
|
||||
}
|
||||
|
||||
AtlasPropertyKey key = management.makePropertyKey(propertyName, propertyClass, cardinality);
|
||||
try {
|
||||
if (propertyClass != Integer.class) {
|
||||
management.addVertexIndexKey(BACKING_INDEX_NAME, key);
|
||||
}
|
||||
} catch(Throwable t) {
|
||||
//ok
|
||||
t.printStackTrace();
|
||||
}
|
||||
try {
|
||||
management.createExactMatchIndex(propertyName, isUnique, Collections.singletonList(key));
|
||||
|
||||
} catch(Throwable t) {
|
||||
//ok
|
||||
t.printStackTrace();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
protected final <V, E> AtlasGraph<V, E> getGraph() {
|
||||
if (graph == null) {
|
||||
graph = new Titan1Graph();
|
||||
}
|
||||
return (AtlasGraph<V, E>)graph;
|
||||
}
|
||||
|
||||
protected Titan1Graph getTitan1Graph() {
|
||||
AtlasGraph g = getGraph();
|
||||
return (Titan1Graph)g;
|
||||
}
|
||||
|
||||
|
||||
protected List<AtlasVertex> newVertices = new ArrayList<>();
|
||||
|
||||
protected final <V, E> AtlasVertex<V, E> createVertex(AtlasGraph<V, E> theGraph) {
|
||||
AtlasVertex<V, E> vertex = theGraph.addVertex();
|
||||
newVertices.add(vertex);
|
||||
return vertex;
|
||||
}
|
||||
|
||||
@AfterMethod
|
||||
public void removeVertices() {
|
||||
for(AtlasVertex vertex : newVertices) {
|
||||
if (vertex.exists()) {
|
||||
getGraph().removeVertex(vertex);
|
||||
}
|
||||
}
|
||||
getGraph().commit();
|
||||
newVertices.clear();
|
||||
}
|
||||
protected void runSynchronouslyInNewThread(final Runnable r) throws Throwable {
|
||||
|
||||
RunnableWrapper wrapper = new RunnableWrapper(r);
|
||||
Thread th = new Thread(wrapper);
|
||||
th.start();
|
||||
th.join();
|
||||
Throwable ex = wrapper.getExceptionThrown();
|
||||
if (ex != null) {
|
||||
throw ex;
|
||||
}
|
||||
}
|
||||
|
||||
private static final class RunnableWrapper implements Runnable {
|
||||
private final Runnable r;
|
||||
private Throwable exceptionThrown = null;
|
||||
|
||||
private RunnableWrapper(Runnable r) {
|
||||
this.r = r;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
r.run();
|
||||
} catch(Throwable e) {
|
||||
exceptionThrown = e;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public Throwable getExceptionThrown() {
|
||||
return exceptionThrown;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,451 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
|
||||
|
||||
import static org.testng.AssertJUnit.assertEquals;
|
||||
import static org.testng.AssertJUnit.assertTrue;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.apache.atlas.AtlasException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery.ComparisionOperator;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
import com.google.common.base.Predicate;
|
||||
import com.google.common.collect.Collections2;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Tests for Titan1GraphQuery.
|
||||
*/
|
||||
@Test
|
||||
public class GraphQueryTest extends AbstractGraphDatabaseTest {
|
||||
|
||||
|
||||
@Test
|
||||
public <V, E> void testQueryThatCannotRunInMemory() throws AtlasException {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
AtlasVertex<V, E> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
|
||||
AtlasVertex<V, E> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
|
||||
graph.commit();
|
||||
|
||||
AtlasVertex<V, E> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Fred");
|
||||
v4.setProperty("size15", "15");
|
||||
|
||||
AtlasGraphQuery q = graph.query();
|
||||
q.has("name", ComparisionOperator.NOT_EQUAL, "George");
|
||||
q.has("size15", "15");
|
||||
graph.commit();
|
||||
pause(); //pause to let the index get updated
|
||||
|
||||
assertQueryMatches(q, v1, v3, v4);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCombinationOfAndsAndOrs() throws AtlasException {
|
||||
Titan1Graph graph = getTitan1Graph();
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
v1.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "George");
|
||||
v2.setProperty("size15", "16");
|
||||
v2.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v3 = createVertex(graph);
|
||||
v3.setProperty("name", "Jane");
|
||||
v3.setProperty("size15", "17");
|
||||
v3.setProperty("typeName", "Person");
|
||||
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Bob");
|
||||
v4.setProperty("size15", "18");
|
||||
v4.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v5 = createVertex(graph);
|
||||
v5.setProperty("name", "Julia");
|
||||
v5.setProperty("size15", "19");
|
||||
v5.setProperty("typeName", "Manager");
|
||||
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("typeName", "Person");
|
||||
//initially match
|
||||
AtlasGraphQuery inner1a = q.createChildQuery();
|
||||
AtlasGraphQuery inner1b = q.createChildQuery();
|
||||
inner1a.has("name", "Fred");
|
||||
inner1b.has("name", "Jane");
|
||||
q.or(toList(inner1a, inner1b));
|
||||
|
||||
|
||||
AtlasGraphQuery inner2a = q.createChildQuery();
|
||||
AtlasGraphQuery inner2b = q.createChildQuery();
|
||||
AtlasGraphQuery inner2c = q.createChildQuery();
|
||||
inner2a.has("size15", "18");
|
||||
inner2b.has("size15", "15");
|
||||
inner2c.has("size15", "16");
|
||||
q.or(toList(inner2a, inner2b, inner2c));
|
||||
|
||||
assertQueryMatches(q, v1);
|
||||
graph.commit();
|
||||
pause(); //let the index update
|
||||
assertQueryMatches(q, v1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWithinStep() throws AtlasException {
|
||||
Titan1Graph graph = getTitan1Graph();
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
v1.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "George");
|
||||
v2.setProperty("size15", "16");
|
||||
v2.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v3 = createVertex(graph);
|
||||
v3.setProperty("name", "Jane");
|
||||
v3.setProperty("size15", "17");
|
||||
v3.setProperty("typeName", "Person");
|
||||
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Bob");
|
||||
v4.setProperty("size15", "18");
|
||||
v4.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v5 = createVertex(graph);
|
||||
v5.setProperty("name", "Julia");
|
||||
v5.setProperty("size15", "19");
|
||||
v5.setProperty("typeName", "Manager");
|
||||
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("typeName", "Person");
|
||||
//initially match
|
||||
q.in("name", toList("Fred", "Jane"));
|
||||
q.in("size15", toList("18", "15", "16"));
|
||||
|
||||
assertQueryMatches(q, v1);
|
||||
graph.commit();
|
||||
pause(); //let the index update
|
||||
assertQueryMatches(q, v1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testWithinStepWhereGraphIsStale() throws AtlasException {
|
||||
Titan1Graph graph = getTitan1Graph();
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
v1.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "George");
|
||||
v2.setProperty("size15", "16");
|
||||
v2.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v3 = createVertex(graph);
|
||||
v3.setProperty("name", "Jane");
|
||||
v3.setProperty("size15", "17");
|
||||
v3.setProperty("typeName", "Person");
|
||||
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Bob");
|
||||
v4.setProperty("size15", "18");
|
||||
v4.setProperty("typeName", "Person");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v5 = createVertex(graph);
|
||||
v5.setProperty("name", "Julia");
|
||||
v5.setProperty("size15", "19");
|
||||
v5.setProperty("typeName", "Manager");
|
||||
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("typeName", "Person");
|
||||
//initially match
|
||||
q.in("name", toList("Fred", "Jane"));
|
||||
|
||||
graph.commit();
|
||||
pause(); //let the index update
|
||||
assertQueryMatches(q, v1, v3);
|
||||
//make v3 no longer match the query. Within step should filter out the vertex since it no longer matches.
|
||||
v3.setProperty("name", "Janet");
|
||||
assertQueryMatches(q, v1);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSimpleOrQuery() throws AtlasException {
|
||||
Titan1Graph graph = getTitan1Graph();
|
||||
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
|
||||
graph.commit();
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Fred");
|
||||
v4.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<Titan1Vertex, Titan1Edge> v5 = createVertex(graph);
|
||||
v5.setProperty("name", "George");
|
||||
v5.setProperty("size15", "16");
|
||||
|
||||
AtlasGraphQuery q = graph.query();
|
||||
AtlasGraphQuery inner1 = q.createChildQuery().has("name", "Fred");
|
||||
AtlasGraphQuery inner2 = q.createChildQuery().has("size15", "15");
|
||||
q.or(toList(inner1, inner2));
|
||||
assertQueryMatches(q, v1, v2, v3, v4);
|
||||
graph.commit();
|
||||
pause(); //pause to let the indexer get updated (this fails frequently without a pause)
|
||||
assertQueryMatches(q, v1, v2, v3, v4);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@Test
|
||||
public <V, E> void testQueryMatchesAddedVertices() throws AtlasException {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
|
||||
AtlasVertex<V, E> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
|
||||
graph.commit();
|
||||
|
||||
AtlasVertex<V, E> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Fred");
|
||||
v4.setProperty("size15", "15");
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("name", "Fred");
|
||||
q.has("size15", "15");
|
||||
|
||||
assertQueryMatches(q, v1, v4);
|
||||
graph.commit();
|
||||
assertQueryMatches(q, v1, v4);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public <V, E> void testQueryDoesNotMatchRemovedVertices() throws AtlasException {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
|
||||
AtlasVertex<V, E> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Fred");
|
||||
v4.setProperty("size15", "15");
|
||||
|
||||
graph.commit();
|
||||
|
||||
graph.removeVertex(v1);
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("name", "Fred");
|
||||
q.has("size15", "15");
|
||||
|
||||
assertQueryMatches(q, v4);
|
||||
graph.commit();
|
||||
|
||||
assertQueryMatches(q, v4);
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testQueryDoesNotMatchUncommittedAddedAndRemovedVertices() throws AtlasException {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = createVertex(graph);
|
||||
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
|
||||
AtlasVertex<V, E> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
|
||||
AtlasVertex<V, E> v4 = createVertex(graph);
|
||||
v4.setProperty("name", "Fred");
|
||||
v4.setProperty("size15", "15");
|
||||
|
||||
|
||||
AtlasGraphQuery q = getGraphQuery();
|
||||
q.has("name", "Fred");
|
||||
q.has("size15", "15");
|
||||
|
||||
assertQueryMatches(q, v1, v4);
|
||||
|
||||
graph.removeVertex(v1);
|
||||
|
||||
|
||||
assertQueryMatches(q, v4);
|
||||
graph.commit();
|
||||
|
||||
assertQueryMatches(q, v4);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public <V, E> void testQueryResultsReflectPropertyAdd() throws AtlasException {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = createVertex(graph);
|
||||
v1.setProperty("name", "Fred");
|
||||
v1.setProperty("size15", "15");
|
||||
v1.addProperty(TRAIT_NAMES, "trait1");
|
||||
v1.addProperty(TRAIT_NAMES, "trait2");
|
||||
|
||||
AtlasVertex<V, E> v2 = createVertex(graph);
|
||||
v2.setProperty("name", "Fred");
|
||||
v2.addProperty(TRAIT_NAMES, "trait1");
|
||||
|
||||
AtlasVertex<V, E> v3 = createVertex(graph);
|
||||
v3.setProperty("size15", "15");
|
||||
v3.addProperty(TRAIT_NAMES, "trait2");
|
||||
|
||||
AtlasGraphQuery query = getGraphQuery();
|
||||
query.has("name", "Fred");
|
||||
query.has(TRAIT_NAMES, "trait1");
|
||||
query.has("size15", "15");
|
||||
|
||||
assertQueryMatches(query, v1);
|
||||
//make v3 match the query
|
||||
v3.setProperty("name", "Fred");
|
||||
v3.addProperty(TRAIT_NAMES, "trait1");
|
||||
assertQueryMatches(query, v1, v3);
|
||||
v3.removeProperty(TRAIT_NAMES);
|
||||
assertQueryMatches(query, v1);
|
||||
v3.addProperty(TRAIT_NAMES, "trait2");
|
||||
assertQueryMatches(query, v1);
|
||||
v1.removeProperty(TRAIT_NAMES);
|
||||
assertQueryMatches(query);
|
||||
graph.commit();
|
||||
assertQueryMatches(query);
|
||||
|
||||
}
|
||||
|
||||
private static <T> List<T> toList(Iterable<T> itr) {
|
||||
List<T> result = new ArrayList<T>();
|
||||
for(T object : itr) {
|
||||
result.add(object);
|
||||
}
|
||||
return result;
|
||||
|
||||
}
|
||||
|
||||
private <V, E> void assertQueryMatches(AtlasGraphQuery expr, AtlasVertex... expectedResults) throws AtlasException {
|
||||
|
||||
//getGraph().commit();
|
||||
Collection<AtlasVertex<Titan1Vertex, Titan1Edge>> temp = toList(expr.vertices());
|
||||
//filter out vertices from previous test executions
|
||||
Collection<AtlasVertex<Titan1Vertex, Titan1Edge>> result =
|
||||
Collections2.filter(temp, new Predicate<AtlasVertex<Titan1Vertex, Titan1Edge>>() {
|
||||
|
||||
@Override
|
||||
public boolean apply(AtlasVertex<Titan1Vertex, Titan1Edge> input) {
|
||||
return newVertices.contains(input);
|
||||
}
|
||||
|
||||
});
|
||||
String errorMessage = "Expected/found result sizes differ. Expected: "
|
||||
+ Arrays.asList(expectedResults).toString() +", found: " + result;
|
||||
assertEquals(errorMessage, expectedResults.length, result.size());
|
||||
|
||||
for(AtlasVertex<V, E> v : expectedResults) {
|
||||
assertTrue(result.contains(v));
|
||||
}
|
||||
}
|
||||
|
||||
private static List<Object> toList(Object...objects) {
|
||||
return Arrays.asList(objects);
|
||||
}
|
||||
|
||||
private AtlasGraphQuery<Titan1Vertex, Titan1Edge> getGraphQuery() {
|
||||
return getTitan1Graph().query();
|
||||
}
|
||||
|
||||
private void pause() {
|
||||
try {
|
||||
Thread.sleep(5000);
|
||||
} catch(InterruptedException e) {
|
||||
//ignore
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,432 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import static org.testng.Assert.assertEquals;
|
||||
import static org.testng.Assert.assertFalse;
|
||||
import static org.testng.Assert.assertNotNull;
|
||||
import static org.testng.Assert.assertNull;
|
||||
import static org.testng.Assert.assertTrue;
|
||||
import static org.testng.Assert.fail;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.math.BigInteger;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
import org.apache.atlas.AtlasException;
|
||||
import org.apache.atlas.repository.Constants;
|
||||
import org.apache.atlas.repository.graphdb.AtlasCardinality;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdge;
|
||||
import org.apache.atlas.repository.graphdb.AtlasEdgeDirection;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphManagement;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraphQuery.ComparisionOperator;
|
||||
import org.apache.atlas.repository.graphdb.AtlasPropertyKey;
|
||||
import org.apache.atlas.repository.graphdb.AtlasVertex;
|
||||
import org.apache.atlas.typesystem.types.DataTypes.TypeCategory;
|
||||
import org.testng.annotations.AfterClass;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
/**
|
||||
* Sanity test of basic graph operations using the Titan 0.5.4 graphdb
|
||||
* abstraction layer implementation.
|
||||
*/
|
||||
public class Titan1DatabaseTest {
|
||||
|
||||
private AtlasGraph<?, ?> atlasGraph;
|
||||
|
||||
private <V, E> AtlasGraph<V, E> getGraph() {
|
||||
if (atlasGraph == null) {
|
||||
Titan1GraphDatabase db = new Titan1GraphDatabase();
|
||||
atlasGraph = db.getGraph();
|
||||
AtlasGraphManagement mgmt = atlasGraph.getManagementSystem();
|
||||
// create the index (which defines these properties as being mult
|
||||
// many)
|
||||
for (String propertyName : new String[]{"__superTypeNames", "__traitNames"}) {
|
||||
AtlasPropertyKey propertyKey = mgmt.getPropertyKey(propertyName);
|
||||
if (propertyKey == null) {
|
||||
propertyKey = mgmt.makePropertyKey(propertyName, String.class, AtlasCardinality.SET);
|
||||
mgmt.createExactMatchIndex(propertyName, false, Collections.singletonList(propertyKey));
|
||||
}
|
||||
}
|
||||
mgmt.commit();
|
||||
}
|
||||
return (AtlasGraph<V, E>) atlasGraph;
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public void cleanup() {
|
||||
atlasGraph.clear();
|
||||
atlasGraph = null;
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testPropertyDataTypes() {
|
||||
|
||||
// primitives
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
testProperty(graph, "booleanProperty", Boolean.TRUE);
|
||||
testProperty(graph, "booleanProperty", Boolean.FALSE);
|
||||
testProperty(graph, "booleanProperty", new Boolean(Boolean.TRUE));
|
||||
testProperty(graph, "booleanProperty", new Boolean(Boolean.FALSE));
|
||||
|
||||
testProperty(graph, "byteProperty", Byte.MAX_VALUE);
|
||||
testProperty(graph, "byteProperty", Byte.MIN_VALUE);
|
||||
testProperty(graph, "byteProperty", new Byte(Byte.MAX_VALUE));
|
||||
testProperty(graph, "byteProperty", new Byte(Byte.MIN_VALUE));
|
||||
|
||||
testProperty(graph, "shortProperty", Short.MAX_VALUE);
|
||||
testProperty(graph, "shortProperty", Short.MIN_VALUE);
|
||||
testProperty(graph, "shortProperty", new Short(Short.MAX_VALUE));
|
||||
testProperty(graph, "shortProperty", new Short(Short.MIN_VALUE));
|
||||
|
||||
testProperty(graph, "intProperty", Integer.MAX_VALUE);
|
||||
testProperty(graph, "intProperty", Integer.MIN_VALUE);
|
||||
testProperty(graph, "intProperty", new Integer(Integer.MAX_VALUE));
|
||||
testProperty(graph, "intProperty", new Integer(Integer.MIN_VALUE));
|
||||
|
||||
testProperty(graph, "longProperty", Long.MIN_VALUE);
|
||||
testProperty(graph, "longProperty", Long.MAX_VALUE);
|
||||
testProperty(graph, "longProperty", new Long(Long.MIN_VALUE));
|
||||
testProperty(graph, "longProperty", new Long(Long.MAX_VALUE));
|
||||
|
||||
testProperty(graph, "doubleProperty", Double.MAX_VALUE);
|
||||
testProperty(graph, "doubleProperty", Double.MIN_VALUE);
|
||||
testProperty(graph, "doubleProperty", new Double(Double.MAX_VALUE));
|
||||
testProperty(graph, "doubleProperty", new Double(Double.MIN_VALUE));
|
||||
|
||||
testProperty(graph, "floatProperty", Float.MAX_VALUE);
|
||||
testProperty(graph, "floatProperty", Float.MIN_VALUE);
|
||||
testProperty(graph, "floatProperty", new Float(Float.MAX_VALUE));
|
||||
testProperty(graph, "floatProperty", new Float(Float.MIN_VALUE));
|
||||
|
||||
// enumerations - TypeCategory
|
||||
testProperty(graph, "typeCategoryProperty", TypeCategory.CLASS);
|
||||
|
||||
// biginteger
|
||||
testProperty(graph, "bigIntegerProperty",
|
||||
new BigInteger(String.valueOf(Long.MAX_VALUE)).multiply(BigInteger.TEN));
|
||||
|
||||
// bigdecimal
|
||||
BigDecimal bigDecimal = new BigDecimal(Double.MAX_VALUE);
|
||||
testProperty(graph, "bigDecimalProperty", bigDecimal.multiply(bigDecimal));
|
||||
}
|
||||
|
||||
private <V, E> void testProperty(AtlasGraph<V, E> graph, String name, Object value) {
|
||||
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
vertex.setProperty(name, value);
|
||||
assertEquals(value, vertex.getProperty(name, value.getClass()));
|
||||
AtlasVertex<V, E> loaded = graph.getVertex(vertex.getId().toString());
|
||||
assertEquals(value, loaded.getProperty(name, value.getClass()));
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testMultiplicityOnePropertySupport() {
|
||||
|
||||
AtlasGraph<V, E> graph = (AtlasGraph<V, E>) getGraph();
|
||||
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
vertex.setProperty("name", "Jeff");
|
||||
vertex.setProperty("location", "Littleton");
|
||||
assertEquals("Jeff", vertex.getProperty("name", String.class));
|
||||
assertEquals("Littleton", vertex.getProperty("location", String.class));
|
||||
|
||||
AtlasVertex<V, E> vertexCopy = graph.getVertex(vertex.getId().toString());
|
||||
|
||||
assertEquals("Jeff", vertexCopy.getProperty("name", String.class));
|
||||
assertEquals("Littleton", vertexCopy.getProperty("location", String.class));
|
||||
|
||||
assertTrue(vertexCopy.getPropertyKeys().contains("name"));
|
||||
assertTrue(vertexCopy.getPropertyKeys().contains("location"));
|
||||
|
||||
assertTrue(vertexCopy.getPropertyValues("name", String.class).contains("Jeff"));
|
||||
assertTrue(vertexCopy.getPropertyValues("location", String.class).contains("Littleton"));
|
||||
assertTrue(vertexCopy.getPropertyValues("test", String.class).isEmpty());
|
||||
assertNull(vertexCopy.getProperty("test", String.class));
|
||||
|
||||
vertex.removeProperty("name");
|
||||
assertFalse(vertex.getPropertyKeys().contains("name"));
|
||||
assertNull(vertex.getProperty("name", String.class));
|
||||
assertTrue(vertex.getPropertyValues("name", String.class).isEmpty());
|
||||
|
||||
vertexCopy = graph.getVertex(vertex.getId().toString());
|
||||
assertFalse(vertexCopy.getPropertyKeys().contains("name"));
|
||||
assertNull(vertexCopy.getProperty("name", String.class));
|
||||
assertTrue(vertexCopy.getPropertyValues("name", String.class).isEmpty());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testRemoveEdge() {
|
||||
|
||||
AtlasGraph<V, E> graph = (AtlasGraph<V, E>) getGraph();
|
||||
AtlasVertex<V, E> v1 = graph.addVertex();
|
||||
AtlasVertex<V, E> v2 = graph.addVertex();
|
||||
|
||||
AtlasEdge<V, E> edge = graph.addEdge(v1, v2, "knows");
|
||||
|
||||
// make sure the edge exists
|
||||
AtlasEdge<V, E> edgeCopy = graph.getEdge(edge.getId().toString());
|
||||
assertNotNull(edgeCopy);
|
||||
assertEquals(edgeCopy, edge);
|
||||
|
||||
graph.removeEdge(edge);
|
||||
|
||||
edgeCopy = graph.getEdge(edge.getId().toString());
|
||||
// should return null now, since edge was deleted
|
||||
assertNull(edgeCopy);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testRemoveVertex() {
|
||||
|
||||
AtlasGraph<V, E> graph = (AtlasGraph<V, E>) getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = graph.addVertex();
|
||||
|
||||
assertNotNull(graph.getVertex(v1.getId().toString()));
|
||||
|
||||
graph.removeVertex(v1);
|
||||
|
||||
assertNull(graph.getVertex(v1.getId().toString()));
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testGetEdges() {
|
||||
|
||||
AtlasGraph<V, E> graph = (AtlasGraph<V, E>) getGraph();
|
||||
AtlasVertex<V, E> v1 = graph.addVertex();
|
||||
AtlasVertex<V, E> v2 = graph.addVertex();
|
||||
AtlasVertex<V, E> v3 = graph.addVertex();
|
||||
|
||||
AtlasEdge<V, E> knows = graph.addEdge(v2, v1, "knows");
|
||||
AtlasEdge<V, E> eats = graph.addEdge(v3, v1, "eats");
|
||||
AtlasEdge<V, E> drives = graph.addEdge(v3, v2, "drives");
|
||||
AtlasEdge<V, E> sleeps = graph.addEdge(v2, v3, "sleeps");
|
||||
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.IN), knows, eats);
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.OUT));
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.BOTH), knows, eats);
|
||||
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.IN, "knows"), knows);
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.OUT, "knows"));
|
||||
assertEdgesMatch(v1.getEdges(AtlasEdgeDirection.BOTH, "knows"), knows);
|
||||
|
||||
assertEdgesMatch(v2.getEdges(AtlasEdgeDirection.IN), drives);
|
||||
assertEdgesMatch(v2.getEdges(AtlasEdgeDirection.OUT), knows, sleeps);
|
||||
assertEdgesMatch(v2.getEdges(AtlasEdgeDirection.BOTH), knows, sleeps, drives);
|
||||
|
||||
assertEdgesMatch(v2.getEdges(AtlasEdgeDirection.BOTH, "delivers"));
|
||||
}
|
||||
|
||||
private <V, E> void assertEdgesMatch(Iterable<AtlasEdge<V, E>> edgesIt, AtlasEdge<V, E>... expected) {
|
||||
List<AtlasEdge<V, E>> edges = toList(edgesIt);
|
||||
assertEquals(expected.length, edges.size());
|
||||
for (AtlasEdge<V, E> edge : expected) {
|
||||
assertTrue(edges.contains(edge));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testMultiplictyManyPropertySupport() {
|
||||
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
String vertexId = vertex.getId().toString();
|
||||
vertex.setProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait1");
|
||||
vertex.setProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait2");
|
||||
assertEquals(vertex.getPropertyValues(Constants.TRAIT_NAMES_PROPERTY_KEY, String.class).size(), 2);
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait3");
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait4");
|
||||
|
||||
assertTrue(vertex.getPropertyKeys().contains(Constants.TRAIT_NAMES_PROPERTY_KEY));
|
||||
validateMultManyPropertiesInVertex(vertex);
|
||||
// fetch a copy of the vertex, make sure result
|
||||
// is the same
|
||||
|
||||
validateMultManyPropertiesInVertex(graph.getVertex(vertexId));
|
||||
|
||||
}
|
||||
|
||||
private <V, E> void validateMultManyPropertiesInVertex(AtlasVertex<V, E> vertex) {
|
||||
|
||||
assertTrue(vertex.getPropertyKeys().contains(Constants.TRAIT_NAMES_PROPERTY_KEY));
|
||||
Collection<String> traitNames = vertex.getPropertyValues(Constants.TRAIT_NAMES_PROPERTY_KEY, String.class);
|
||||
assertTrue(traitNames.contains("trait1"));
|
||||
assertTrue(traitNames.contains("trait2"));
|
||||
assertTrue(traitNames.contains("trait3"));
|
||||
assertTrue(traitNames.contains("trait4"));
|
||||
|
||||
try {
|
||||
vertex.getProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, String.class);
|
||||
fail("Expected exception not thrown");
|
||||
} catch (IllegalStateException expected) {
|
||||
// multiple property values exist
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testListProperties() throws AtlasException {
|
||||
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
List<String> colorsToSet = new ArrayList<String>();
|
||||
colorsToSet.add("red");
|
||||
colorsToSet.add("blue");
|
||||
colorsToSet.add("green");
|
||||
vertex.setListProperty("colors", colorsToSet);
|
||||
List<String> colors = vertex.getListProperty("colors");
|
||||
assertTrue(colors.contains("red"));
|
||||
assertTrue(colors.contains("blue"));
|
||||
assertTrue(colors.contains("green"));
|
||||
|
||||
AtlasVertex<V, E> vertexCopy = graph.getVertex(vertex.getId().toString());
|
||||
colors = vertexCopy.getListProperty("colors");
|
||||
assertTrue(colors.contains("red"));
|
||||
assertTrue(colors.contains("blue"));
|
||||
assertTrue(colors.contains("green"));
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testRemoveProperty() {
|
||||
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait1");
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait1");
|
||||
vertex.setProperty("name", "Jeff");
|
||||
|
||||
// remove existing property - multiplicity one
|
||||
vertex.removeProperty("jeff");
|
||||
|
||||
assertFalse(vertex.getPropertyKeys().contains("jeff"));
|
||||
|
||||
// remove existing property - multiplicity many
|
||||
vertex.removeProperty(Constants.TRAIT_NAMES_PROPERTY_KEY);
|
||||
assertFalse(vertex.getPropertyKeys().contains(Constants.TRAIT_NAMES_PROPERTY_KEY));
|
||||
|
||||
AtlasVertex<V, E> vertexCopy = graph.getVertex(vertex.getId().toString());
|
||||
assertFalse(vertexCopy.getPropertyKeys().contains("jeff"));
|
||||
assertFalse(vertexCopy.getPropertyKeys().contains(Constants.TRAIT_NAMES_PROPERTY_KEY));
|
||||
|
||||
// remove non-existing property
|
||||
vertex.removeProperty(Constants.TRAIT_NAMES_PROPERTY_KEY);
|
||||
vertex.removeProperty("jeff");
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void getGetGraphQueryForVertices() {
|
||||
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
|
||||
AtlasVertex<V, E> v1 = graph.addVertex();
|
||||
AtlasVertex<V, E> v2 = graph.addVertex();
|
||||
AtlasVertex<V, E> v3 = graph.addVertex();
|
||||
|
||||
v1.setProperty("name", "Jeff");
|
||||
v1.setProperty("weight", 1);
|
||||
|
||||
v2.setProperty("name", "Fred");
|
||||
v2.setProperty("weight", 2);
|
||||
|
||||
v3.setProperty("name", "Chris");
|
||||
v3.setProperty("weight", 3);
|
||||
|
||||
AtlasEdge<V, E> knows = graph.addEdge(v2, v1, "knows");
|
||||
knows.setProperty("weight", 1);
|
||||
AtlasEdge<V, E> eats = graph.addEdge(v3, v1, "eats");
|
||||
eats.setProperty("weight", 2);
|
||||
AtlasEdge<V, E> drives = graph.addEdge(v3, v2, "drives");
|
||||
drives.setProperty("weight", 3);
|
||||
|
||||
AtlasEdge<V, E> sleeps = graph.addEdge(v2, v3, "sleeps");
|
||||
sleeps.setProperty("weight", 4);
|
||||
|
||||
testExecuteGraphQuery("name", null, "Jeff", v1);
|
||||
testExecuteGraphQuery("weight", ComparisionOperator.EQUAL, 2, v2);
|
||||
testExecuteGraphQuery("weight", ComparisionOperator.GREATER_THAN_EQUAL, 2, v2, v3);
|
||||
testExecuteGraphQuery("weight", ComparisionOperator.LESS_THAN_EQUAL, 2, v2, v1);
|
||||
|
||||
}
|
||||
|
||||
private <V, E> void testExecuteGraphQuery(String property, ComparisionOperator op, Object value,
|
||||
AtlasVertex<V, E>... expected) {
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
AtlasGraphQuery<V, E> query = graph.query();
|
||||
if (op != null) {
|
||||
query.has(property, op, value);
|
||||
} else {
|
||||
query.has(property, value);
|
||||
}
|
||||
Iterable<? extends AtlasVertex<V, E>> result = query.vertices();
|
||||
List<AtlasVertex<V, E>> list = toList(result);
|
||||
assertEquals(expected.length, list.size());
|
||||
for (AtlasVertex<V, E> vertex : expected) {
|
||||
assertTrue(list.contains(vertex));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public <V, E> void testAddMultManyPropertyValueTwice() {
|
||||
|
||||
AtlasGraph<V, E> graph = getGraph();
|
||||
String vertexId;
|
||||
|
||||
AtlasVertex<V, E> vertex = graph.addVertex();
|
||||
vertexId = vertex.getId().toString();
|
||||
vertex.setProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait1");
|
||||
vertex.setProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait1");
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait2");
|
||||
vertex.addProperty(Constants.TRAIT_NAMES_PROPERTY_KEY, "trait2");
|
||||
|
||||
validateDuplicatePropertyVertex(vertex);
|
||||
|
||||
// fetch a copy of the vertex, make sure result is the same
|
||||
|
||||
validateDuplicatePropertyVertex(graph.getVertex(vertexId));
|
||||
}
|
||||
|
||||
private <V, E> void validateDuplicatePropertyVertex(AtlasVertex<V, E> vertex) {
|
||||
assertEquals(2, vertex.getPropertyValues(Constants.TRAIT_NAMES_PROPERTY_KEY, String.class).size());
|
||||
assertTrue(vertex.getPropertyKeys().contains(Constants.TRAIT_NAMES_PROPERTY_KEY));
|
||||
Collection<String> traitNames = vertex.getPropertyValues(Constants.TRAIT_NAMES_PROPERTY_KEY, String.class);
|
||||
assertTrue(traitNames.contains("trait1"));
|
||||
assertTrue(traitNames.contains("trait2"));
|
||||
}
|
||||
|
||||
private static <T> List<T> toList(Iterable<? extends T> iterable) {
|
||||
List<T> result = new ArrayList<T>();
|
||||
for (T item : iterable) {
|
||||
result.add(item);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,77 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.atlas.repository.graphdb.titan1;
|
||||
|
||||
import org.apache.atlas.ApplicationProperties;
|
||||
import org.apache.atlas.AtlasException;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.commons.configuration.Configuration;
|
||||
import org.testng.Assert;
|
||||
import org.testng.annotations.AfterClass;
|
||||
import org.testng.annotations.BeforeTest;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
@Test
|
||||
public class TitanGraphProviderTest {
|
||||
|
||||
private Configuration configuration;
|
||||
private AtlasGraph<?, ?> graph;
|
||||
|
||||
@BeforeTest
|
||||
public void setUp() throws AtlasException {
|
||||
//First get Instance
|
||||
graph = new Titan1Graph();
|
||||
configuration = ApplicationProperties.getSubsetConfiguration(ApplicationProperties.get(),
|
||||
Titan1GraphDatabase.GRAPH_PREFIX);
|
||||
}
|
||||
|
||||
@AfterClass
|
||||
public void tearDown() throws Exception {
|
||||
try {
|
||||
graph.shutdown();
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
try {
|
||||
graph.clear();
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testValidate() throws AtlasException {
|
||||
try {
|
||||
Titan1GraphDatabase.validateIndexBackend(configuration);
|
||||
} catch (Exception e) {
|
||||
Assert.fail("Unexpected exception ", e);
|
||||
}
|
||||
|
||||
//Change backend
|
||||
configuration.setProperty(Titan1GraphDatabase.INDEX_BACKEND_CONF, Titan1GraphDatabase.INDEX_BACKEND_LUCENE);
|
||||
try {
|
||||
Titan1GraphDatabase.validateIndexBackend(configuration);
|
||||
Assert.fail("Expected exception");
|
||||
} catch (Exception e) {
|
||||
Assert.assertEquals(e.getMessage(),
|
||||
"Configured Index Backend lucene differs from earlier configured "
|
||||
+ "Index Backend elasticsearch. Aborting!");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,97 @@
|
|||
#
|
||||
# Licensed to the Apache Software Foundation (ASF) under one
|
||||
# or more contributor license agreements. See the NOTICE file
|
||||
# distributed with this work for additional information
|
||||
# regarding copyright ownership. The ASF licenses this file
|
||||
# to you under the Apache License, Version 2.0 (the
|
||||
# "License"); you may not use this file except in compliance
|
||||
# with the License. You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
#
|
||||
|
||||
######### Graph Database to Use #########
|
||||
atlas.graphdb.backend=org.apache.atlas.repository.graphdb.titan1.Titan1Database
|
||||
|
||||
######### Atlas Server Configs #########
|
||||
atlas.rest.address=http://localhost:31000
|
||||
|
||||
######### Graph Database Configs #########
|
||||
# Graph Storage
|
||||
atlas.graph.storage.backend=${titan.storage.backend}
|
||||
|
||||
# Graph Search Index Backend
|
||||
atlas.graph.index.search.backend=${titan.index.backend}
|
||||
|
||||
#Berkeley storage directory
|
||||
atlas.graph.storage.directory=${sys:atlas.data}/berkley
|
||||
|
||||
#hbase
|
||||
#For standalone mode , specify localhost
|
||||
#for distributed mode, specify zookeeper quorum here - For more information refer http://s3.thinkaurelius.com/docs/titan/current/hbase.html#_remote_server_mode_2
|
||||
|
||||
atlas.graph.storage.hostname=${titan.storage.hostname}
|
||||
atlas.graph.storage.hbase.regions-per-server=1
|
||||
atlas.graph.storage.lock.wait-time=10000
|
||||
|
||||
#ElasticSearch
|
||||
atlas.graph.index.search.directory=${sys:atlas.data}/es
|
||||
atlas.graph.index.search.elasticsearch.client-only=false
|
||||
atlas.graph.index.search.elasticsearch.local-mode=true
|
||||
atlas.graph.index.search.elasticsearch.create.sleep=2000
|
||||
|
||||
# Solr cloud mode properties
|
||||
atlas.graph.index.search.solr.mode=cloud
|
||||
atlas.graph.index.search.solr.zookeeper-url=${solr.zk.address}
|
||||
|
||||
|
||||
######### Hive Lineage Configs #########
|
||||
# This models reflects the base super types for Data and Process
|
||||
#atlas.lineage.hive.table.type.name=DataSet
|
||||
#atlas.lineage.hive.process.type.name=Process
|
||||
#atlas.lineage.hive.process.inputs.name=inputs
|
||||
#atlas.lineage.hive.process.outputs.name=outputs
|
||||
|
||||
## Schema
|
||||
atlas.lineage.hive.table.schema.query.hive_table=hive_table where name='%s'\, columns
|
||||
|
||||
######### Notification Configs #########
|
||||
atlas.notification.embedded=true
|
||||
|
||||
atlas.kafka.zookeeper.connect=localhost:19026
|
||||
atlas.kafka.bootstrap.servers=localhost:19027
|
||||
atlas.kafka.data=${sys:atlas.data}/kafka
|
||||
atlas.kafka.zookeeper.session.timeout.ms=4000
|
||||
atlas.kafka.zookeeper.sync.time.ms=20
|
||||
atlas.kafka.consumer.timeout.ms=100
|
||||
atlas.kafka.auto.commit.interval.ms=100
|
||||
atlas.kafka.hook.group.id=atlas
|
||||
atlas.kafka.entities.group.id=atlas_entities
|
||||
|
||||
######### Entity Audit Configs #########
|
||||
atlas.audit.hbase.tablename=ATLAS_ENTITY_AUDIT_EVENTS
|
||||
atlas.audit.zookeeper.session.timeout.ms=1000
|
||||
atlas.audit.hbase.zookeeper.quorum=localhost
|
||||
atlas.audit.hbase.zookeeper.property.clientPort=19026
|
||||
|
||||
######### Security Properties #########
|
||||
|
||||
# SSL config
|
||||
atlas.enableTLS=false
|
||||
atlas.server.https.port=31443
|
||||
|
||||
######### Security Properties #########
|
||||
|
||||
hbase.security.authentication=simple
|
||||
|
||||
atlas.hook.falcon.synchronous=true
|
||||
######### High Availability Configuration ########
|
||||
atlas.server.ha.enabled=false
|
||||
#atlas.server.ids=id1
|
||||
#atlas.server.address.id1=localhost:21000
|
||||
35
pom.xml
35
pom.xml
|
|
@ -490,7 +490,7 @@
|
|||
<titan.storage.backend>berkeleyje</titan.storage.backend>
|
||||
<titan.index.backend>elasticsearch</titan.index.backend>
|
||||
<entity.repository.impl>org.apache.atlas.repository.audit.InMemoryEntityAuditRepository</entity.repository.impl>
|
||||
<graphdb.backend.impl>org.apache.atlas.repository.graphdb.titan0.Titan0GraphDatabase</graphdb.backend.impl>
|
||||
<graphdb.backend.impl>org.apache.atlas.repository.graphdb.titan0.Titan0GraphDatabase</graphdb.backend.impl>
|
||||
<atlas.surefire.options></atlas.surefire.options>
|
||||
|
||||
<aspectj.runtime.version>1.8.7</aspectj.runtime.version>
|
||||
|
|
@ -533,6 +533,28 @@
|
|||
<skipDocs>false</skipDocs>
|
||||
</properties>
|
||||
</profile>
|
||||
<profile>
|
||||
<id>titan1</id>
|
||||
<properties>
|
||||
<graphdb.backend.impl>org.apache.atlas.repository.graphdb.titan1.Titan1GraphDatabase</graphdb.backend.impl>
|
||||
</properties>
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-impls</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<type>pom</type>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-titan0</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<modules>
|
||||
|
|
@ -1251,9 +1273,14 @@
|
|||
<artifactId>atlas-graphdb-impls</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<type>pom</type>
|
||||
<!-- exclusions should be added here for all of the non-titan0 implementations -->
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<!-- exclusions for all of the non-titan0 implementations -->
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-titan1</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@ ATLAS-1060 Add composite indexes for exact match performance improvements for al
|
|||
ATLAS-1127 Modify creation and modification timestamps to Date instead of Long(sumasai)
|
||||
|
||||
ALL CHANGES:
|
||||
ATLAS-695: Add Titan 1.0.0 support to Atlas (guptaneeru via jnhagelberg)
|
||||
ATLAS-1552: automatic update of inverse references in V2 code path (dkantor)
|
||||
ATLAS-1603: fix to handle null value for object_id type attributes (mneethiraj via kevalbhatt)
|
||||
ATLAS 1607: notify listeners on classification addition/deletion (sarathkumarsubramanian via mneethiraj)
|
||||
|
|
|
|||
|
|
@ -53,6 +53,7 @@ import org.apache.atlas.repository.graph.GraphBackedMetadataRepository;
|
|||
import org.apache.atlas.repository.graph.GraphBackedSearchIndexer;
|
||||
import org.apache.atlas.repository.graph.GraphHelper;
|
||||
import org.apache.atlas.repository.graphdb.AtlasGraph;
|
||||
import org.apache.atlas.repository.graphdb.GremlinVersion;
|
||||
import org.apache.atlas.repository.typestore.GraphBackedTypeStore;
|
||||
import org.apache.atlas.repository.typestore.ITypeStore;
|
||||
import org.apache.atlas.services.DefaultMetadataService;
|
||||
|
|
@ -85,6 +86,7 @@ import org.apache.commons.configuration.Configuration;
|
|||
import org.apache.commons.lang.RandomStringUtils;
|
||||
import org.codehaus.jettison.json.JSONArray;
|
||||
import org.testng.Assert;
|
||||
import org.testng.SkipException;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.google.common.collect.ImmutableSet;
|
||||
|
|
@ -778,4 +780,12 @@ public final class TestUtils {
|
|||
checker.removeAll(actual);
|
||||
assertEquals(checker.size(), 0);
|
||||
}
|
||||
|
||||
public static void skipForGremlin3EnabledGraphDb() throws SkipException {
|
||||
//ATLAS-1579 Currently, some tests are skipped for titan1 backened. As these tests are hard coded to use Gremlin2. See ATLAS-1579, ATLAS-1591 once it is fixed, please remove it.
|
||||
if (TestUtils.getGraph().getSupportedGremlinVersion() == GremlinVersion.THREE) {
|
||||
throw new SkipException ("This test requires Gremlin2. Skipping test ");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -49,6 +49,7 @@ import org.apache.atlas.repository.Constants;
|
|||
import org.apache.atlas.repository.MetadataRepository;
|
||||
import org.apache.atlas.repository.graph.AtlasGraphProvider;
|
||||
import org.apache.atlas.repository.graph.GraphBackedSearchIndexer;
|
||||
import org.apache.atlas.repository.graphdb.GremlinVersion;
|
||||
import org.apache.atlas.type.AtlasTypeRegistry;
|
||||
import org.apache.atlas.typesystem.ITypedReferenceableInstance;
|
||||
import org.apache.atlas.typesystem.Referenceable;
|
||||
|
|
@ -63,6 +64,7 @@ import org.codehaus.jettison.json.JSONArray;
|
|||
import org.codehaus.jettison.json.JSONException;
|
||||
import org.codehaus.jettison.json.JSONObject;
|
||||
import org.testng.Assert;
|
||||
import org.testng.SkipException;
|
||||
import org.testng.annotations.AfterClass;
|
||||
import org.testng.annotations.BeforeClass;
|
||||
import org.testng.annotations.BeforeMethod;
|
||||
|
|
@ -275,6 +277,7 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
|
||||
@Test
|
||||
public void testRawSearch1() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
// Query for all Vertices in Graph
|
||||
Object r = discoveryService.searchByGremlin("g.V.toList()");
|
||||
Assert.assertTrue(r instanceof List);
|
||||
|
|
@ -398,7 +401,7 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
{"hive_db has name", 3},
|
||||
{"hive_db, hive_table", 10},
|
||||
{"View is JdbcAccess", 2},
|
||||
{"hive_db as db1, hive_table where db1.name = \"Reporting\"", 0}, //Not working - ATLAS-145
|
||||
{"hive_db as db1, hive_table where db1.name = \"Reporting\"", isGremlin3() ? 4 : 0}, //Not working in with Titan 0 - ATLAS-145
|
||||
// - Final working query -> discoveryService.searchByGremlin("L:{_var_0 = [] as Set;g.V().has(\"__typeName\", \"hive_db\").fill(_var_0);g.V().has(\"__superTypeNames\", \"hive_db\").fill(_var_0);_var_0._().as(\"db1\").in(\"__hive_table.db\").back(\"db1\").and(_().has(\"hive_db.name\", T.eq, \"Reporting\")).toList()}")
|
||||
/*
|
||||
{"hive_db, hive_process has name"}, //Invalid query
|
||||
|
|
@ -419,7 +422,7 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
{"hive_db where hive_db is JdbcAccess", 0}, //Not supposed to work
|
||||
{"hive_db hive_table", 10},
|
||||
{"hive_db where hive_db has name", 3},
|
||||
{"hive_db as db1 hive_table where (db1.name = \"Reporting\")", 0}, //Not working -> ATLAS-145
|
||||
{"hive_db as db1 hive_table where (db1.name = \"Reporting\")", isGremlin3() ? 4 : 0}, //Not working in Titan 0 -> ATLAS-145
|
||||
{"hive_db where (name = \"Reporting\") select name as _col_0, (createTime + 1) as _col_1 ", 1},
|
||||
{"hive_table where (name = \"sales_fact\" and createTime > \"2014-01-01\" ) select name as _col_0, createTime as _col_1 ", 1},
|
||||
{"hive_table where (name = \"sales_fact\" and createTime >= \"2014-12-11T02:35:58.440Z\" ) select name as _col_0, createTime as _col_1 ", 1},
|
||||
|
|
@ -528,7 +531,7 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
{"View is JdbcAccess", 2},
|
||||
{"View is JdbcAccess limit 1", 1},
|
||||
{"View is JdbcAccess limit 2 offset 1", 1},
|
||||
{"hive_db as db1, hive_table where db1.name = \"Reporting\"", 0}, //Not working - ATLAS-145
|
||||
{"hive_db as db1, hive_table where db1.name = \"Reporting\"", isGremlin3() ? 4 : 0}, //Not working in Titan 0 - ATLAS-145
|
||||
|
||||
|
||||
{"from hive_table", 10},
|
||||
|
|
@ -586,7 +589,7 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
{"hive_db where hive_db has name limit 2 offset 0", 2},
|
||||
{"hive_db where hive_db has name limit 2 offset 1", 2},
|
||||
|
||||
{"hive_db as db1 hive_table where (db1.name = \"Reporting\")", 0}, //Not working -> ATLAS-145
|
||||
{"hive_db as db1 hive_table where (db1.name = \"Reporting\")", isGremlin3() ? 4 : 0}, //Not working in Titan 0 -> ATLAS-145
|
||||
{"hive_db where (name = \"Reporting\") select name as _col_0, (createTime + 1) as _col_1 ", 1},
|
||||
{"hive_db where (name = \"Reporting\") select name as _col_0, (createTime + 1) as _col_1 limit 10", 1},
|
||||
{"hive_db where (name = \"Reporting\") select name as _col_0, (createTime + 1) as _col_1 limit 10 offset 1", 0},
|
||||
|
|
@ -1252,4 +1255,8 @@ public class GraphBackedDiscoveryServiceTest extends BaseRepositoryTest {
|
|||
private FieldValueValidator makeNoResultsValidator() {
|
||||
return new FieldValueValidator();
|
||||
}
|
||||
|
||||
private boolean isGremlin3() {
|
||||
return TestUtils.getGraph().getSupportedGremlinVersion() == GremlinVersion.THREE;
|
||||
}
|
||||
}
|
||||
|
|
@ -18,18 +18,30 @@
|
|||
|
||||
package org.apache.atlas.lineage;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import static org.testng.Assert.assertEquals;
|
||||
import static org.testng.Assert.assertNotNull;
|
||||
import static org.testng.Assert.assertTrue;
|
||||
import static org.testng.Assert.fail;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.apache.atlas.AtlasClient;
|
||||
import org.apache.atlas.AtlasErrorCode;
|
||||
import org.apache.atlas.BaseRepositoryTest;
|
||||
import org.apache.atlas.RepositoryMetadataModule;
|
||||
import org.apache.atlas.TestUtils;
|
||||
import org.apache.atlas.discovery.EntityLineageService;
|
||||
import org.apache.atlas.exception.AtlasBaseException;
|
||||
import org.apache.atlas.model.instance.AtlasEntity.Status;
|
||||
import org.apache.atlas.model.instance.AtlasEntityHeader;
|
||||
import org.apache.atlas.model.lineage.AtlasLineageInfo;
|
||||
import org.apache.atlas.model.lineage.AtlasLineageInfo.LineageRelation;
|
||||
import org.apache.atlas.model.lineage.AtlasLineageInfo.LineageDirection;
|
||||
import org.apache.atlas.model.lineage.AtlasLineageInfo.LineageRelation;
|
||||
import org.apache.atlas.typesystem.Referenceable;
|
||||
import org.apache.atlas.typesystem.persistence.Id;
|
||||
import org.apache.commons.collections.ArrayStack;
|
||||
|
|
@ -37,17 +49,12 @@ import org.apache.commons.lang.RandomStringUtils;
|
|||
import org.testng.Assert;
|
||||
import org.testng.annotations.AfterClass;
|
||||
import org.testng.annotations.BeforeClass;
|
||||
import org.testng.annotations.BeforeMethod;
|
||||
import org.testng.annotations.DataProvider;
|
||||
import org.testng.annotations.Guice;
|
||||
import org.testng.annotations.Test;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import static org.testng.Assert.*;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
/**
|
||||
* Unit tests for the new v2 Instance LineageService.
|
||||
|
|
@ -73,6 +80,7 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
*/
|
||||
@Test
|
||||
public void testCircularLineage() throws Exception{
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String entityGuid = getEntityId(HIVE_TABLE_TYPE, "name", "table2");
|
||||
AtlasLineageInfo circularLineage = getInputLineageInfo(entityGuid, 5);
|
||||
|
||||
|
|
@ -108,6 +116,7 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
|
||||
@Test
|
||||
public void testGetInputLineageInfo() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String entityGuid = getEntityId(HIVE_TABLE_TYPE, "name", "sales_fact_monthly_mv");
|
||||
AtlasLineageInfo inputLineage = getInputLineageInfo(entityGuid, 4);
|
||||
|
||||
|
|
@ -143,6 +152,7 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
|
||||
@Test
|
||||
public void testGetOutputLineageInfo() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String entityGuid = getEntityId(HIVE_TABLE_TYPE, "name", "sales_fact");
|
||||
AtlasLineageInfo outputLineage = getOutputLineageInfo(entityGuid, 4);
|
||||
|
||||
|
|
@ -178,6 +188,7 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
|
||||
@Test
|
||||
public void testGetLineageInfo() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String entityGuid = getEntityId(HIVE_TABLE_TYPE, "name", "sales_fact_monthly_mv");
|
||||
AtlasLineageInfo bothLineage = getBothLineageInfo(entityGuid, 5);
|
||||
|
||||
|
|
@ -241,6 +252,7 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
|
||||
@Test
|
||||
public void testNewLineageWithDelete() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String tableName = "table" + random();
|
||||
createTable(tableName, 3, true);
|
||||
String entityGuid = getEntityId(HIVE_TABLE_TYPE, "name", tableName);
|
||||
|
|
@ -344,4 +356,5 @@ public class EntityLineageServiceTest extends BaseRepositoryTest {
|
|||
private String getEntityId(String typeName, String attributeName, String attributeValue) throws Exception {
|
||||
return repository.getEntityDefinition(typeName, attributeName, attributeValue).getId()._getId();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -19,6 +19,7 @@
|
|||
package org.apache.atlas.repository.audit;
|
||||
|
||||
import org.apache.atlas.EntityAuditEvent;
|
||||
import org.apache.atlas.TestUtils;
|
||||
import org.apache.atlas.typesystem.Referenceable;
|
||||
import org.apache.commons.lang.RandomStringUtils;
|
||||
import org.testng.annotations.BeforeTest;
|
||||
|
|
@ -44,6 +45,7 @@ public class AuditRepositoryTestBase {
|
|||
|
||||
@Test
|
||||
public void testAddEvents() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
EntityAuditEvent event = new EntityAuditEvent(rand(), System.currentTimeMillis(), "u1",
|
||||
EntityAuditEvent.EntityAuditAction.ENTITY_CREATE, "d1", new Referenceable(rand()));
|
||||
|
||||
|
|
@ -57,6 +59,7 @@ public class AuditRepositoryTestBase {
|
|||
|
||||
@Test
|
||||
public void testListPagination() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
String id1 = "id1" + rand();
|
||||
String id2 = "id2" + rand();
|
||||
String id3 = "id3" + rand();
|
||||
|
|
@ -90,6 +93,7 @@ public class AuditRepositoryTestBase {
|
|||
|
||||
@Test
|
||||
public void testInvalidEntityId() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
List<EntityAuditEvent> events = eventRepository.listEvents(rand(), null, (short) 3);
|
||||
assertEquals(events.size(), 0);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@ package org.apache.atlas.repository.audit;
|
|||
|
||||
import org.apache.atlas.ApplicationProperties;
|
||||
import org.apache.atlas.EntityAuditEvent;
|
||||
import org.apache.atlas.TestUtils;
|
||||
import org.apache.commons.configuration.Configuration;
|
||||
import org.apache.hadoop.hbase.TableName;
|
||||
import org.apache.hadoop.hbase.client.Admin;
|
||||
|
|
@ -36,6 +37,9 @@ public class HBaseBasedAuditRepositoryTest extends AuditRepositoryTestBase {
|
|||
|
||||
@BeforeClass
|
||||
public void setup() throws Exception {
|
||||
//ATLAS-1591 Currently, some tests are skipped for titan1 backened. As these tests are hard coded to use Gremlin2. See ATLAS-1591 once it is fixed, please remove it.
|
||||
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
eventRepository = new HBaseBasedAuditRepository();
|
||||
HBaseTestUtils.startCluster();
|
||||
((HBaseBasedAuditRepository) eventRepository).start();
|
||||
|
|
@ -54,6 +58,7 @@ public class HBaseBasedAuditRepositoryTest extends AuditRepositoryTestBase {
|
|||
|
||||
@Test
|
||||
public void testTableCreated() throws Exception {
|
||||
TestUtils.skipForGremlin3EnabledGraphDb();
|
||||
Connection connection = HBaseTestUtils.getConnection();
|
||||
Admin admin = connection.getAdmin();
|
||||
assertTrue(admin.tableExists(tableName));
|
||||
|
|
|
|||
170
webapp/pom.xml
170
webapp/pom.xml
|
|
@ -34,8 +34,8 @@
|
|||
<properties>
|
||||
<projectBaseDir>${project.basedir}/..</projectBaseDir>
|
||||
<debug.jetty.daemon>true</debug.jetty.daemon>
|
||||
<log4j.configuration.url>file:///${project.build.directory}/../../distro/src/conf/atlas-log4j.xml</log4j.configuration.url>
|
||||
<packages.to.exclude />
|
||||
<log4j.configuration.url>file://${project.build.directory}/../../distro/src/conf/atlas-log4j.xml</log4j.configuration.url>
|
||||
</properties>
|
||||
|
||||
<profiles>
|
||||
|
|
@ -46,7 +46,7 @@
|
|||
<activeByDefault>false</activeByDefault>
|
||||
</activation>
|
||||
<properties>
|
||||
<packages.to.exclude>WEB-INF/lib/titan-berkeleyje-${titan.version}.jar,WEB-INF/lib/je-*.jar,WEB-INF/lib/titan-es-${titan.version}.jar,WEB-INF/lib/elasticsearch-*.jar</packages.to.exclude>
|
||||
<packages.to.exclude>WEB-INF/lib/titan-*.jar,WEB-INF/lib/je-*.jar,WEB-INF/lib/elasticsearch-*.jar,WEB-INF/lib/lucene-*.jar</packages.to.exclude>
|
||||
</properties>
|
||||
</profile>
|
||||
|
||||
|
|
@ -59,7 +59,6 @@
|
|||
<packages.to.exclude>WEB-INF/lib/je-*.jar</packages.to.exclude>
|
||||
</properties>
|
||||
</profile>
|
||||
|
||||
<profile>
|
||||
<id>Windows</id>
|
||||
<activation>
|
||||
|
|
@ -68,9 +67,48 @@
|
|||
</os>
|
||||
</activation>
|
||||
<properties>
|
||||
<log4j.configuration.url>file:/${project.build.directory}/../../distro/src/conf/atlas-log4j.xml</log4j.configuration.url>
|
||||
<log4j.configuration.url>file:/${project.build.directory}/../../distro/src/conf/atlas-log4j.xml</log4j.configuration.url>
|
||||
</properties>
|
||||
</profile>
|
||||
</profile>
|
||||
<profile>
|
||||
<id>titan1</id>
|
||||
<!-- remove conflicting lucene/titan versions from catalog when using titan 1 -->
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-catalog</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>com.thinkaurelius.titan</groupId>
|
||||
<artifactId>titan-core</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-core</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-queryparser</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.apache.lucene</groupId>
|
||||
<artifactId>lucene-analyzers-common</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-catalog</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
<dependencies>
|
||||
|
|
@ -79,7 +117,6 @@
|
|||
<artifactId>atlas-graphdb-impls</artifactId>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-common</artifactId>
|
||||
|
|
@ -100,27 +137,26 @@
|
|||
<artifactId>atlas-client</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-authorization</artifactId>
|
||||
<version>${project.version}</version>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-notification</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-intg</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.hadoop</groupId>
|
||||
<artifactId>hadoop-common</artifactId>
|
||||
</dependency>
|
||||
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.hadoop</groupId>
|
||||
<artifactId>hadoop-minikdc</artifactId>
|
||||
|
|
@ -136,6 +172,11 @@
|
|||
<artifactId>atlas-catalog</artifactId>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-graphdb-impls</artifactId>
|
||||
<type>pom</type>
|
||||
</dependency>
|
||||
<!-- Zookeeper, curator -->
|
||||
<dependency>
|
||||
<groupId>org.apache.curator</groupId>
|
||||
|
|
@ -155,8 +196,9 @@
|
|||
<dependency>
|
||||
<groupId>org.apache.zookeeper</groupId>
|
||||
<artifactId>zookeeper</artifactId>
|
||||
</dependency>
|
||||
|
||||
|
||||
</dependency>
|
||||
<!-- supports simple auth handler -->
|
||||
<dependency>
|
||||
<groupId>org.apache.httpcomponents</groupId>
|
||||
|
|
@ -274,61 +316,61 @@
|
|||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-core</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-core</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-webmvc</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-webmvc</artifactId>
|
||||
<version>${spring.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-core</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-core</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-web</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-web</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-config</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-config</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-ldap</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
<groupId>org.springframework.security</groupId>
|
||||
<artifactId>spring-security-ldap</artifactId>
|
||||
<version>${spring.security.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.servlet</groupId>
|
||||
<artifactId>javax.servlet-api</artifactId>
|
||||
<version>${javax.servlet.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.ldap</groupId>
|
||||
<artifactId>spring-ldap-core</artifactId>
|
||||
<version>${spring-ldap-core.version}</version>
|
||||
<groupId>org.springframework.ldap</groupId>
|
||||
<artifactId>spring-ldap-core</artifactId>
|
||||
<version>${spring-ldap-core.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-dashboardv2</artifactId>
|
||||
<type>war</type>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.servlet</groupId>
|
||||
<artifactId>javax.servlet-api</artifactId>
|
||||
<version>${javax.servlet.version}</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.easymock</groupId>
|
||||
<artifactId>easymock</artifactId>
|
||||
|
|
@ -342,15 +384,13 @@
|
|||
<classifier>tests</classifier>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.apache.atlas</groupId>
|
||||
<artifactId>atlas-intg</artifactId>
|
||||
<classifier>tests</classifier>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<dependency>
|
||||
<groupId>com.nimbusds</groupId>
|
||||
<artifactId>nimbus-jose-jwt</artifactId>
|
||||
<version>3.9</version>
|
||||
|
|
@ -393,7 +433,7 @@
|
|||
<artifactId>atlas-dashboardv2</artifactId>
|
||||
</overlay>
|
||||
<overlay>
|
||||
<!-- empty groupId/artifactId represents the current build -->
|
||||
<!-- empty groupId/artifactId represents the current build -->
|
||||
</overlay>
|
||||
</overlays>
|
||||
<archive>
|
||||
|
|
@ -439,7 +479,7 @@
|
|||
</configuration>
|
||||
</plugin>
|
||||
|
||||
<!-- Running unit tests in pre-integration-test phase after war is built -->
|
||||
<!-- Running unit tests in pre-integration-test phase after war is built -->
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-surefire-plugin</artifactId>
|
||||
|
|
@ -448,7 +488,7 @@
|
|||
<user.dir>${project.basedir}</user.dir>
|
||||
<projectBaseDir>${project.basedir}/..</projectBaseDir>
|
||||
</systemProperties>
|
||||
<!--<skipTests>true</skipTests>-->
|
||||
<!--<skipTests>true</skipTests> -->
|
||||
<forkMode>always</forkMode>
|
||||
<redirectTestOutputToFile>true</redirectTestOutputToFile>
|
||||
<argLine>-Djava.awt.headless=true -Dproject.version=${project.version}
|
||||
|
|
@ -494,8 +534,7 @@
|
|||
<webApp>
|
||||
<contextPath>/</contextPath>
|
||||
<descriptor>${project.basedir}/src/test/webapp/WEB-INF/web.xml</descriptor>
|
||||
<!-- ${project.build.directory}/atlas-webapp-${project.version} -->
|
||||
<extraClasspath>${project.build.directory}/../../webapp/target/test-classes/</extraClasspath>
|
||||
<extraClasspath>${project.build.testOutputDirectory}</extraClasspath>
|
||||
</webApp>
|
||||
<useTestScope>true</useTestScope>
|
||||
<systemProperties>
|
||||
|
|
@ -511,14 +550,18 @@
|
|||
<name>atlas.log.dir</name>
|
||||
<value>${project.build.directory}/logs</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<name>atlas.graphdb.backend</name>
|
||||
<value>${graphdb.backend.impl}</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<name>keystore.file</name>
|
||||
<value>${project.build.directory}/../../webapp/target/atlas.keystore
|
||||
<value>${project.build.directory}/atlas.keystore
|
||||
</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<name>truststore.file</name>
|
||||
<value>${project.build.directory}/../../webapp/target/atlas.keystore</value>
|
||||
<value>${project.build.directory}/atlas.keystore</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<name>atlas.home</name>
|
||||
|
|
@ -528,6 +571,10 @@
|
|||
<name>atlas.data</name>
|
||||
<value>${project.build.directory}/data</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<name>atlas.graphdb.backend</name>
|
||||
<value>${graphdb.backend.impl}</value>
|
||||
</systemProperty>
|
||||
<systemProperty>
|
||||
<key>atlas.conf</key>
|
||||
<value>${project.build.directory}/../../typesystem/target/test-classes</value>
|
||||
|
|
@ -537,26 +584,9 @@
|
|||
<stopPort>31001</stopPort>
|
||||
<stopWait>${jetty-maven-plugin.stopWait}</stopWait>
|
||||
<daemon>${debug.jetty.daemon}</daemon>
|
||||
<testClassesDirectory>${project.build.directory}/../../webapp/target/test-classes/</testClassesDirectory>
|
||||
<testClassesDirectory>${project.build.testOutputDirectory}</testClassesDirectory>
|
||||
<useTestClasspath>true</useTestClasspath>
|
||||
</configuration>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.eclipse.jetty</groupId>
|
||||
<artifactId>jetty-jsp</artifactId>
|
||||
<version>${jetty.version}</version>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>javax.servlet</groupId>
|
||||
<artifactId>*</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>org.glassfish</groupId>
|
||||
<artifactId>javax.el</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>start-jetty</id>
|
||||
|
|
@ -578,7 +608,7 @@
|
|||
<groupId>net.alchim31.maven</groupId>
|
||||
<artifactId>scala-maven-plugin</artifactId>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-resources-plugin</artifactId>
|
||||
<executions>
|
||||
|
|
@ -655,4 +685,6 @@
|
|||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
|
||||
</project>
|
||||
|
|
|
|||
Loading…
Reference in New Issue