Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
A
atlas
Project
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
dataplatform
atlas
Commits
bff013f0
Commit
bff013f0
authored
Jul 18, 2016
by
Madhan Neethiraj
Committed by
Suma Shivaprasad
Jul 18, 2016
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
ATLAS-1030: performance trace instrumentation for REST APIs
parent
e895819f
Show whitespace changes
Inline
Side-by-side
Showing
11 changed files
with
521 additions
and
2 deletions
+521
-2
AtlasPerfTracer.java
...src/main/java/org/apache/atlas/utils/AtlasPerfTracer.java
+80
-0
atlas-log4j.xml
distro/src/conf/atlas-log4j.xml
+16
-0
atlas-log4j.xml
typesystem/src/main/resources/atlas-log4j.xml
+16
-0
AdminResource.java
...in/java/org/apache/atlas/web/resources/AdminResource.java
+40
-0
DataSetLineageResource.java
...rg/apache/atlas/web/resources/DataSetLineageResource.java
+23
-0
EntityResource.java
...n/java/org/apache/atlas/web/resources/EntityResource.java
+84
-0
EntityService.java
...in/java/org/apache/atlas/web/resources/EntityService.java
+62
-1
LineageResource.java
.../java/org/apache/atlas/web/resources/LineageResource.java
+23
-0
MetadataDiscoveryResource.java
...apache/atlas/web/resources/MetadataDiscoveryResource.java
+30
-0
TaxonomyService.java
.../java/org/apache/atlas/web/resources/TaxonomyService.java
+117
-1
TypesResource.java
...in/java/org/apache/atlas/web/resources/TypesResource.java
+30
-0
No files found.
common/src/main/java/org/apache/atlas/utils/AtlasPerfTracer.java
0 → 100644
View file @
bff013f0
/**
* 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
.
utils
;
import
org.slf4j.Logger
;
import
org.slf4j.LoggerFactory
;
/**
* Handles logging of performance measurements.
*/
public
final
class
AtlasPerfTracer
{
protected
final
Logger
logger
;
protected
final
String
tag
;
private
final
long
startTimeMs
;
private
static
long
reportingThresholdMs
=
0L
;
public
static
Logger
getPerfLogger
(
String
name
)
{
return
LoggerFactory
.
getLogger
(
"org.apache.atlas.perf."
+
name
);
}
public
static
Logger
getPerfLogger
(
Class
<?>
cls
)
{
return
AtlasPerfTracer
.
getPerfLogger
(
cls
.
getName
());
}
public
static
boolean
isPerfTraceEnabled
(
Logger
logger
)
{
return
logger
.
isDebugEnabled
();
}
public
static
AtlasPerfTracer
getPerfTracer
(
Logger
logger
,
String
tag
)
{
return
new
AtlasPerfTracer
(
logger
,
tag
);
}
public
static
void
log
(
AtlasPerfTracer
tracer
)
{
if
(
tracer
!=
null
)
{
tracer
.
log
();
}
}
private
AtlasPerfTracer
(
Logger
logger
,
String
tag
)
{
this
.
logger
=
logger
;
this
.
tag
=
tag
;
startTimeMs
=
System
.
currentTimeMillis
();
}
public
String
getTag
()
{
return
tag
;
}
public
long
getStartTime
()
{
return
startTimeMs
;
}
public
long
getElapsedTime
()
{
return
System
.
currentTimeMillis
()
-
startTimeMs
;
}
public
void
log
()
{
long
elapsedTime
=
getElapsedTime
();
if
(
elapsedTime
>
reportingThresholdMs
)
{
logger
.
debug
(
"PERF|"
+
tag
+
"|"
+
elapsedTime
);
}
}
}
distro/src/conf/atlas-log4j.xml
View file @
bff013f0
...
...
@@ -48,6 +48,22 @@
<appender-ref
ref=
"FILE"
/>
</logger>
<!-- uncomment this block to generate performance traces
<appender name="perf_appender" class="org.apache.log4j.DailyRollingFileAppender">
<param name="file" value="${atlas.log.dir}/atlas_perf.log" />
<param name="datePattern" value="'.'yyyy-MM-dd" />
<param name="append" value="true" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d|%t|%m%n" />
</layout>
</appender>
<logger name="org.apache.atlas.perf" additivity="false">
<level value="debug" />
<appender-ref ref="perf_appender" />
</logger>
-->
<logger
name=
"com.thinkaurelius.titan"
additivity=
"false"
>
<level
value=
"warn"
/>
<appender-ref
ref=
"FILE"
/>
...
...
typesystem/src/main/resources/atlas-log4j.xml
View file @
bff013f0
...
...
@@ -41,6 +41,22 @@
<appender-ref
ref=
"console"
/>
</logger>
<!-- uncomment this block to generate performance traces
<appender name="perf_appender" class="org.apache.log4j.DailyRollingFileAppender">
<param name="file" value="${atlas.log.dir}/atlas_perf.log" />
<param name="datePattern" value="'.'yyyy-MM-dd" />
<param name="append" value="true" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%d|%t|%m%n" />
</layout>
</appender>
<logger name="org.apache.atlas.perf" additivity="false">
<level value="debug" />
<appender-ref ref="perf_appender" />
</logger>
-->
<logger
name=
"com.thinkaurelius.titan"
additivity=
"false"
>
<level
value=
"info"
/>
<appender-ref
ref=
"console"
/>
...
...
webapp/src/main/java/org/apache/atlas/web/resources/AdminResource.java
View file @
bff013f0
...
...
@@ -31,6 +31,7 @@ import javax.ws.rs.core.MediaType;
import
javax.ws.rs.core.Response
;
import
org.apache.atlas.AtlasClient
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.filters.AtlasCSRFPreventionFilter
;
import
org.apache.atlas.web.service.ServiceState
;
import
org.apache.atlas.web.util.Servlets
;
...
...
@@ -39,6 +40,7 @@ import org.apache.commons.configuration.PropertiesConfiguration;
import
org.apache.commons.lang.StringUtils
;
import
org.codehaus.jettison.json.JSONException
;
import
org.codehaus.jettison.json.JSONObject
;
import
org.slf4j.Logger
;
import
org.springframework.security.core.Authentication
;
import
org.springframework.security.core.GrantedAuthority
;
import
org.springframework.security.core.context.SecurityContextHolder
;
...
...
@@ -51,6 +53,7 @@ import com.google.inject.Inject;
@Path
(
"admin"
)
@Singleton
public
class
AdminResource
{
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.AdminResource"
);
private
static
final
String
isCSRF_ENABLED
=
"atlas.rest-csrf.enabled"
;
private
static
final
String
BROWSER_USER_AGENT_PARAM
=
"atlas.rest-csrf.browser-useragents-regex"
;
...
...
@@ -75,6 +78,13 @@ public class AdminResource {
@Path
(
"stack"
)
@Produces
(
MediaType
.
TEXT_PLAIN
)
public
String
getThreadDump
()
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"AdminResource.getThreadDump()"
);
}
ThreadGroup
topThreadGroup
=
Thread
.
currentThread
().
getThreadGroup
();
while
(
topThreadGroup
.
getParent
()
!=
null
)
{
...
...
@@ -91,6 +101,9 @@ public class AdminResource {
builder
.
append
(
stackTrace
);
}
return
builder
.
toString
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
/**
...
...
@@ -102,6 +115,13 @@ public class AdminResource {
@Path
(
"version"
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getVersion
()
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"AdminResource.getVersion()"
);
}
if
(
version
==
null
)
{
try
{
PropertiesConfiguration
configProperties
=
new
PropertiesConfiguration
(
"atlas-buildinfo.properties"
);
...
...
@@ -121,12 +141,22 @@ public class AdminResource {
}
return
version
;
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
@Path
(
"status"
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getStatus
()
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"AdminResource.getStatus()"
);
}
JSONObject
responseData
=
new
JSONObject
();
try
{
responseData
.
put
(
AtlasClient
.
STATUS
,
serviceState
.
getState
().
toString
());
...
...
@@ -135,6 +165,9 @@ public class AdminResource {
}
catch
(
JSONException
e
)
{
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -143,7 +176,12 @@ public class AdminResource {
public
Response
getUserProfile
()
{
JSONObject
responseData
=
new
JSONObject
();
Boolean
enableTaxonomy
=
null
;
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"AdminResource.getUserProfile()"
);
}
PropertiesConfiguration
configProperties
=
new
PropertiesConfiguration
(
"atlas-application.properties"
);
enableTaxonomy
=
new
Boolean
(
configProperties
.
getString
(
isTaxonomyEnabled
,
"false"
));
Authentication
auth
=
SecurityContextHolder
.
getContext
().
getAuthentication
();
...
...
@@ -170,6 +208,8 @@ public class AdminResource {
return
response
;
}
catch
(
JSONException
|
ConfigurationException
e
)
{
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
}
webapp/src/main/java/org/apache/atlas/web/resources/DataSetLineageResource.java
View file @
bff013f0
...
...
@@ -22,6 +22,7 @@ import org.apache.atlas.AtlasClient;
import
org.apache.atlas.discovery.DiscoveryException
;
import
org.apache.atlas.discovery.LineageService
;
import
org.apache.atlas.typesystem.exception.EntityNotFoundException
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.codehaus.jettison.json.JSONObject
;
import
org.slf4j.Logger
;
...
...
@@ -47,6 +48,7 @@ import javax.ws.rs.core.Response;
public
class
DataSetLineageResource
{
private
static
final
Logger
LOG
=
LoggerFactory
.
getLogger
(
DataSetLineageResource
.
class
);
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.DataSetLineageResource"
);
private
final
LineageService
lineageService
;
...
...
@@ -73,7 +75,12 @@ public class DataSetLineageResource {
public
Response
inputsGraph
(
@Context
HttpServletRequest
request
,
@PathParam
(
"tableName"
)
String
tableName
)
{
LOG
.
info
(
"Fetching lineage inputs graph for tableName={}"
,
tableName
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"DataSetLineageResource.inputsGraph("
+
tableName
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getInputsGraph
(
tableName
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -91,6 +98,8 @@ public class DataSetLineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get lineage inputs graph for table {}"
,
tableName
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -106,7 +115,12 @@ public class DataSetLineageResource {
public
Response
outputsGraph
(
@Context
HttpServletRequest
request
,
@PathParam
(
"tableName"
)
String
tableName
)
{
LOG
.
info
(
"Fetching lineage outputs graph for tableName={}"
,
tableName
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"DataSetLineageResource.outputsGraph("
+
tableName
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getOutputsGraph
(
tableName
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -124,6 +138,8 @@ public class DataSetLineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get lineage outputs graph for table {}"
,
tableName
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -139,7 +155,12 @@ public class DataSetLineageResource {
public
Response
schema
(
@Context
HttpServletRequest
request
,
@PathParam
(
"tableName"
)
String
tableName
)
{
LOG
.
info
(
"Fetching schema for tableName={}"
,
tableName
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"DataSetLineageResource.schema("
+
tableName
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getSchema
(
tableName
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -157,6 +178,8 @@ public class DataSetLineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get schema for table {}"
,
tableName
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
}
webapp/src/main/java/org/apache/atlas/web/resources/EntityResource.java
View file @
bff013f0
...
...
@@ -33,6 +33,7 @@ import org.apache.atlas.typesystem.exception.TypeNotFoundException;
import
org.apache.atlas.typesystem.json.InstanceSerialization
;
import
org.apache.atlas.typesystem.types.ValueConversionException
;
import
org.apache.atlas.utils.ParamChecker
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.apache.commons.lang.StringUtils
;
import
org.codehaus.jettison.json.JSONArray
;
...
...
@@ -77,6 +78,8 @@ import java.util.List;
public
class
EntityResource
{
private
static
final
Logger
LOG
=
LoggerFactory
.
getLogger
(
EntityResource
.
class
);
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.EntityResource"
);
private
static
final
String
TRAIT_NAME
=
"traitName"
;
private
final
MetadataService
metadataService
;
...
...
@@ -106,7 +109,12 @@ public class EntityResource {
public
Response
submit
(
@Context
HttpServletRequest
request
)
{
String
entityJson
=
null
;
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.submit()"
);
}
String
entities
=
Servlets
.
getRequestPayload
(
request
);
//Handle backward compatibility - if entities is not JSONArray, convert to JSONArray
...
...
@@ -142,6 +150,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to persist entity instance entityDef={}"
,
entityJson
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -185,7 +195,12 @@ public class EntityResource {
public
Response
updateEntities
(
@Context
HttpServletRequest
request
)
{
String
entityJson
=
null
;
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.updateEntities()"
);
}
final
String
entities
=
Servlets
.
getRequestPayload
(
request
);
entityJson
=
AtlasClient
.
toString
(
new
JSONArray
(
entities
));
...
...
@@ -208,6 +223,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to persist entity instance entityDef={}"
,
entityJson
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -249,7 +266,12 @@ public class EntityResource {
@QueryParam
(
"value"
)
String
value
,
@Context
HttpServletRequest
request
)
{
String
entityJson
=
null
;
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.updateByUniqueAttribute()"
);
}
entityJson
=
Servlets
.
getRequestPayload
(
request
);
LOG
.
info
(
"Partially updating entity by unique attribute {} {} {} {} "
,
entityType
,
attribute
,
value
,
entityJson
);
...
...
@@ -278,6 +300,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to partially update entity {} {} "
+
entityType
+
":"
+
attribute
+
"."
+
value
,
entityJson
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -296,11 +320,20 @@ public class EntityResource {
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
updateEntityByGuid
(
@PathParam
(
"guid"
)
String
guid
,
@QueryParam
(
"property"
)
String
attribute
,
@Context
HttpServletRequest
request
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.updateEntityByGuid()"
);
}
if
(
StringUtils
.
isEmpty
(
attribute
))
{
return
updateEntityPartialByGuid
(
guid
,
request
);
}
else
{
return
updateEntityAttributeByGuid
(
guid
,
attribute
,
request
);
}
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
private
Response
updateEntityPartialByGuid
(
String
guid
,
HttpServletRequest
request
)
{
...
...
@@ -384,7 +417,12 @@ public class EntityResource {
@QueryParam
(
"property"
)
String
attribute
,
@QueryParam
(
"value"
)
String
value
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.deleteEntities()"
);
}
AtlasClient
.
EntityResult
entityResult
;
if
(
guids
!=
null
&&
!
guids
.
isEmpty
())
{
LOG
.
info
(
"Deleting entities {}"
,
guids
);
...
...
@@ -409,6 +447,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to delete entities {} {} {} {} "
,
guids
,
entityType
,
attribute
,
value
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -421,7 +461,12 @@ public class EntityResource {
@Path
(
"{guid}"
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getEntityDefinition
(
@PathParam
(
"guid"
)
String
guid
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.getEntityDefinition()"
);
}
LOG
.
debug
(
"Fetching entity definition for guid={} "
,
guid
);
ParamChecker
.
notEmpty
(
guid
,
"guid cannot be null"
);
final
String
entityDefinition
=
metadataService
.
getEntityDefinition
(
guid
);
...
...
@@ -449,6 +494,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get instance definition for GUID {}"
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -489,6 +536,12 @@ public class EntityResource {
public
Response
getEntity
(
@QueryParam
(
"type"
)
String
entityType
,
@QueryParam
(
"property"
)
String
attribute
,
@QueryParam
(
"value"
)
String
value
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.getEntity("
+
entityType
+
", "
+
attribute
+
", "
+
value
+
")"
);
}
if
(
StringUtils
.
isEmpty
(
attribute
))
{
//List API
return
getEntityListByType
(
entityType
);
...
...
@@ -496,6 +549,9 @@ public class EntityResource {
//Get entity by unique attribute
return
getEntityDefinitionByAttribute
(
entityType
,
attribute
,
value
);
}
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
/**
...
...
@@ -553,7 +609,12 @@ public class EntityResource {
@Path
(
"{guid}/traits"
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getTraitNames
(
@PathParam
(
"guid"
)
String
guid
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.getTraitNames("
+
guid
+
")"
);
}
LOG
.
debug
(
"Fetching trait names for entity={}"
,
guid
);
final
List
<
String
>
traitNames
=
metadataService
.
getTraitNames
(
guid
);
...
...
@@ -572,6 +633,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get trait names for entity {}"
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -586,7 +649,12 @@ public class EntityResource {
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
addTrait
(
@Context
HttpServletRequest
request
,
@PathParam
(
"guid"
)
final
String
guid
)
{
String
traitDefinition
=
null
;
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.addTrait("
+
guid
+
")"
);
}
traitDefinition
=
Servlets
.
getRequestPayload
(
request
);
LOG
.
info
(
"Adding trait={} for entity={} "
,
traitDefinition
,
guid
);
metadataService
.
addTrait
(
guid
,
traitDefinition
);
...
...
@@ -608,6 +676,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to add trait for entity={} traitDef={}"
,
guid
,
traitDefinition
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -624,7 +694,12 @@ public class EntityResource {
public
Response
deleteTrait
(
@Context
HttpServletRequest
request
,
@PathParam
(
"guid"
)
String
guid
,
@PathParam
(
TRAIT_NAME
)
String
traitName
)
{
LOG
.
info
(
"Deleting trait={} from entity={} "
,
traitName
,
guid
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.deleteTrait("
+
guid
+
", "
+
traitName
+
")"
);
}
metadataService
.
deleteTrait
(
guid
,
traitName
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -644,6 +719,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to delete trait name={} for entity={}"
,
traitName
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -664,7 +741,12 @@ public class EntityResource {
@QueryParam
(
"count"
)
@DefaultValue
(
"100"
)
short
count
)
{
LOG
.
debug
(
"Audit events request for entity {}, start key {}, number of results required {}"
,
guid
,
startKey
,
count
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityResource.getAuditEvents("
+
guid
+
", "
+
startKey
+
", "
+
count
+
")"
);
}
List
<
EntityAuditEvent
>
events
=
metadataService
.
getAuditEvents
(
guid
,
startKey
,
count
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -677,6 +759,8 @@ public class EntityResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get audit events for entity guid={} startKey={}"
,
guid
,
startKey
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
webapp/src/main/java/org/apache/atlas/web/resources/EntityService.java
View file @
bff013f0
...
...
@@ -22,7 +22,9 @@ import org.apache.atlas.AtlasException;
import
org.apache.atlas.catalog.*
;
import
org.apache.atlas.catalog.exception.CatalogException
;
import
org.apache.atlas.services.MetadataService
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.slf4j.Logger
;
import
javax.inject.Inject
;
import
javax.inject.Singleton
;
...
...
@@ -36,6 +38,7 @@ import java.util.*;
@Path
(
"v1/entities"
)
@Singleton
public
class
EntityService
extends
BaseService
{
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.EntityService"
);
private
final
EntityResourceProvider
entityResourceProvider
;
private
final
EntityTagResourceProvider
entityTagResourceProvider
;
...
...
@@ -50,12 +53,21 @@ public class EntityService extends BaseService {
@GET
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getEntities
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.getEntities()"
);
}
String
queryString
=
decode
(
getQueryString
(
ui
));
BaseRequest
request
=
new
CollectionRequest
(
Collections
.<
String
,
Object
>
emptyMap
(),
queryString
);
Result
result
=
getResources
(
entityResourceProvider
,
request
);
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -64,11 +76,19 @@ public class EntityService extends BaseService {
public
Response
getEntity
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"entityId"
)
String
entityId
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.getEntity("
+
entityId
+
")"
);
}
BaseRequest
request
=
new
InstanceRequest
(
Collections
.<
String
,
Object
>
singletonMap
(
"id"
,
entityId
));
Result
result
=
getResource
(
entityResourceProvider
,
request
);
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -78,6 +98,11 @@ public class EntityService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"entityId"
)
String
entityId
,
@PathParam
(
"tag"
)
String
tagName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.getEntityTag("
+
entityId
+
", "
+
tagName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"id"
,
entityId
);
...
...
@@ -85,6 +110,9 @@ public class EntityService extends BaseService {
Result
result
=
getResource
(
entityTagResourceProvider
,
new
InstanceRequest
(
properties
));
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -93,12 +121,20 @@ public class EntityService extends BaseService {
public
Response
getEntityTags
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"entityId"
)
String
entityGuid
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.getEntityTags("
+
entityGuid
+
")"
);
}
BaseRequest
request
=
new
CollectionRequest
(
Collections
.<
String
,
Object
>
singletonMap
(
"id"
,
entityGuid
),
decode
(
getQueryString
(
ui
)));
Result
result
=
getResources
(
entityTagResourceProvider
,
request
);
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@POST
...
...
@@ -109,6 +145,11 @@ public class EntityService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"entityId"
)
String
entityId
,
@PathParam
(
"tag"
)
String
tagName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.tagEntity("
+
entityId
+
", "
+
tagName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"id"
,
entityId
);
...
...
@@ -117,6 +158,9 @@ public class EntityService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
CREATED
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
201
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@POST
...
...
@@ -124,6 +168,11 @@ public class EntityService extends BaseService {
public
Response
tagEntities
(
String
body
,
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.tagEntities()"
);
}
Map
<
String
,
Object
>
properties
=
parsePayload
(
body
);
...
...
@@ -142,7 +191,11 @@ public class EntityService extends BaseService {
}
return
Response
.
status
(
Response
.
Status
.
CREATED
).
entity
(
new
GenericEntity
<
Collection
<
Results
>>(
result
)
{}).
build
();
new
GenericEntity
<
Collection
<
Results
>>(
result
)
{
}).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@DELETE
...
...
@@ -152,6 +205,11 @@ public class EntityService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"entityId"
)
String
entityId
,
@PathParam
(
"tag"
)
String
tagName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"EntityService.deleteEntityTag()"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"id"
,
entityId
);
...
...
@@ -160,5 +218,8 @@ public class EntityService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
}
webapp/src/main/java/org/apache/atlas/web/resources/LineageResource.java
View file @
bff013f0
...
...
@@ -22,6 +22,7 @@ import org.apache.atlas.AtlasClient;
import
org.apache.atlas.discovery.DiscoveryException
;
import
org.apache.atlas.discovery.LineageService
;
import
org.apache.atlas.typesystem.exception.EntityNotFoundException
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.codehaus.jettison.json.JSONObject
;
import
org.slf4j.Logger
;
...
...
@@ -41,6 +42,7 @@ import javax.ws.rs.core.Response;
@Singleton
public
class
LineageResource
{
private
static
final
Logger
LOG
=
LoggerFactory
.
getLogger
(
DataSetLineageResource
.
class
);
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.LineageResource"
);
private
final
LineageService
lineageService
;
...
...
@@ -67,7 +69,12 @@ public class LineageResource {
public
Response
inputsGraph
(
@PathParam
(
"guid"
)
String
guid
)
{
LOG
.
info
(
"Fetching lineage inputs graph for guid={}"
,
guid
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"LineageResource.inputsGraph("
+
guid
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getInputsGraphForEntity
(
guid
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -84,6 +91,8 @@ public class LineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get lineage inputs graph for entity guid={}"
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -99,7 +108,12 @@ public class LineageResource {
public
Response
outputsGraph
(
@PathParam
(
"guid"
)
String
guid
)
{
LOG
.
info
(
"Fetching lineage outputs graph for entity guid={}"
,
guid
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"LineageResource.outputsGraph("
+
guid
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getOutputsGraphForEntity
(
guid
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -116,6 +130,8 @@ public class LineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get lineage outputs graph for entity guid={}"
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -131,7 +147,12 @@ public class LineageResource {
public
Response
schema
(
@PathParam
(
"guid"
)
String
guid
)
{
LOG
.
info
(
"Fetching schema for entity guid={}"
,
guid
);
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"LineageResource.schema("
+
guid
+
")"
);
}
final
String
jsonResult
=
lineageService
.
getSchemaForEntity
(
guid
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -148,6 +169,8 @@ public class LineageResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get schema for entity={}"
,
guid
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
}
webapp/src/main/java/org/apache/atlas/web/resources/MetadataDiscoveryResource.java
View file @
bff013f0
...
...
@@ -20,6 +20,7 @@ package org.apache.atlas.web.resources;
import
com.google.common.base.Preconditions
;
import
org.apache.atlas.AtlasClient
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.utils.ParamChecker
;
import
org.apache.atlas.discovery.DiscoveryException
;
import
org.apache.atlas.discovery.DiscoveryService
;
...
...
@@ -51,6 +52,7 @@ import org.apache.hadoop.classification.InterfaceAudience;
public
class
MetadataDiscoveryResource
{
private
static
final
Logger
LOG
=
LoggerFactory
.
getLogger
(
MetadataDiscoveryResource
.
class
);
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.MetadataDiscoveryResource"
);
private
static
final
String
QUERY_TYPE_DSL
=
"dsl"
;
private
static
final
String
QUERY_TYPE_GREMLIN
=
"gremlin"
;
private
static
final
String
QUERY_TYPE_FULLTEXT
=
"full-text"
;
...
...
@@ -80,7 +82,12 @@ public class MetadataDiscoveryResource {
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
search
(
@QueryParam
(
"query"
)
String
query
)
{
JSONObject
response
;
AtlasPerfTracer
perf
=
null
;
try
{
// fall back to dsl
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"MetadataDiscoveryResource.search("
+
query
+
")"
);
}
ParamChecker
.
notEmpty
(
query
,
"query cannot be null"
);
final
String
jsonResultStr
=
discoveryService
.
searchByDSL
(
query
);
...
...
@@ -94,6 +101,8 @@ public class MetadataDiscoveryResource {
}
catch
(
Throwable
throwable
)
{
LOG
.
error
(
"Unable to get entity list for query {} using dsl"
,
query
,
throwable
);
return
searchUsingFullText
(
query
);
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -108,7 +117,12 @@ public class MetadataDiscoveryResource {
@Consumes
(
Servlets
.
JSON_MEDIA_TYPE
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
searchUsingQueryDSL
(
@QueryParam
(
"query"
)
String
dslQuery
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"MetadataDiscoveryResource.searchUsingQueryDSL("
+
dslQuery
+
")"
);
}
ParamChecker
.
notEmpty
(
dslQuery
,
"dslQuery cannot be null"
);
final
String
jsonResultStr
=
discoveryService
.
searchByDSL
(
dslQuery
);
...
...
@@ -121,6 +135,8 @@ public class MetadataDiscoveryResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get entity list for dslQuery {}"
,
dslQuery
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -136,7 +152,12 @@ public class MetadataDiscoveryResource {
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
@InterfaceAudience
.
Private
public
Response
searchUsingGremlinQuery
(
@QueryParam
(
"query"
)
String
gremlinQuery
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"MetadataDiscoveryResource.searchUsingGremlinQuery("
+
gremlinQuery
+
")"
);
}
ParamChecker
.
notEmpty
(
gremlinQuery
,
"gremlinQuery cannot be null or empty"
);
final
List
<
Map
<
String
,
String
>>
results
=
discoveryService
.
searchByGremlin
(
gremlinQuery
);
...
...
@@ -159,6 +180,8 @@ public class MetadataDiscoveryResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get entity list for gremlinQuery {}"
,
gremlinQuery
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -173,7 +196,12 @@ public class MetadataDiscoveryResource {
@Consumes
(
Servlets
.
JSON_MEDIA_TYPE
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
searchUsingFullText
(
@QueryParam
(
"query"
)
String
query
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"MetadataDiscoveryResource.searchUsingFullText("
+
query
+
")"
);
}
ParamChecker
.
notEmpty
(
query
,
"query cannot be null or empty"
);
final
String
jsonResultStr
=
discoveryService
.
searchByFullText
(
query
);
JSONArray
rowsJsonArr
=
new
JSONArray
(
jsonResultStr
);
...
...
@@ -186,6 +214,8 @@ public class MetadataDiscoveryResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get entity list for query {}"
,
query
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
webapp/src/main/java/org/apache/atlas/web/resources/TaxonomyService.java
View file @
bff013f0
...
...
@@ -24,7 +24,9 @@ import org.apache.atlas.catalog.Request;
import
org.apache.atlas.catalog.exception.CatalogException
;
import
org.apache.atlas.catalog.exception.InvalidPayloadException
;
import
org.apache.atlas.services.MetadataService
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.slf4j.Logger
;
import
javax.inject.Inject
;
import
javax.inject.Singleton
;
...
...
@@ -41,6 +43,7 @@ import java.util.Map;
@Path
(
"v1/taxonomies"
)
@Singleton
public
class
TaxonomyService
extends
BaseService
{
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.TaxonomyService"
);
private
ResourceProvider
taxonomyResourceProvider
;
private
ResourceProvider
termResourceProvider
;
...
...
@@ -58,20 +61,37 @@ public class TaxonomyService extends BaseService {
public
Response
getTaxonomy
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.getTaxonomy("
+
taxonomyName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"name"
,
taxonomyName
);
Result
result
=
getResource
(
taxonomyResourceProvider
,
new
InstanceRequest
(
properties
));
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getTaxonomies
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.getTaxonomies()"
);
}
String
queryString
=
decode
(
getQueryString
(
ui
));
Request
request
=
new
CollectionRequest
(
Collections
.<
String
,
Object
>
emptyMap
(),
queryString
);
Result
result
=
getResources
(
taxonomyResourceProvider
,
request
);
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@POST
...
...
@@ -81,6 +101,11 @@ public class TaxonomyService extends BaseService {
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.createTaxonomy("
+
taxonomyName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
parsePayload
(
body
);
properties
.
put
(
"name"
,
taxonomyName
);
...
...
@@ -89,6 +114,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
CREATED
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
201
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@PUT
...
...
@@ -98,6 +126,11 @@ public class TaxonomyService extends BaseService {
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.updateTaxonomy("
+
taxonomyName
+
")"
);
}
Map
<
String
,
Object
>
queryProperties
=
new
HashMap
<>();
queryProperties
.
put
(
"name"
,
taxonomyName
);
...
...
@@ -106,6 +139,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@DELETE
...
...
@@ -114,6 +150,11 @@ public class TaxonomyService extends BaseService {
public
Response
deleteTaxonomy
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.deleteTaxonomy("
+
taxonomyName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"name"
,
taxonomyName
);
...
...
@@ -122,6 +163,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -131,6 +175,11 @@ public class TaxonomyService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.getTaxonomyTerm("
+
taxonomyName
+
", "
+
termName
+
")"
);
}
TermPath
termPath
=
new
TermPath
(
taxonomyName
,
termName
);
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
...
...
@@ -138,6 +187,9 @@ public class TaxonomyService extends BaseService {
Result
result
=
getResource
(
termResourceProvider
,
new
InstanceRequest
(
properties
));
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -146,6 +198,11 @@ public class TaxonomyService extends BaseService {
public
Response
getTaxonomyTerms
(
@Context
HttpHeaders
headers
,
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.getTaxonomyTerms("
+
taxonomyName
+
")"
);
}
String
queryString
=
decode
(
getQueryString
(
ui
));
TermPath
termPath
=
new
TermPath
(
taxonomyName
,
null
);
...
...
@@ -154,6 +211,9 @@ public class TaxonomyService extends BaseService {
Result
result
=
getResources
(
termResourceProvider
,
request
);
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@GET
...
...
@@ -164,6 +224,11 @@ public class TaxonomyService extends BaseService {
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"rootTerm"
)
String
rootTerm
,
@PathParam
(
"remainder"
)
String
remainder
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.getSubTerms("
+
taxonomyName
+
", "
+
rootTerm
+
", "
+
remainder
+
")"
);
}
Result
result
;
String
termName
=
String
.
format
(
"%s%s"
,
rootTerm
,
...
...
@@ -184,6 +249,9 @@ public class TaxonomyService extends BaseService {
}
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
getSerializer
().
serialize
(
result
,
ui
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@POST
...
...
@@ -194,6 +262,11 @@ public class TaxonomyService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.createTerm("
+
taxonomyName
+
", "
+
termName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
parsePayload
(
body
);
validateName
(
termName
);
...
...
@@ -202,6 +275,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
CREATED
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
201
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@POST
...
...
@@ -213,16 +289,24 @@ public class TaxonomyService extends BaseService {
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
,
@PathParam
(
"remainder"
)
String
remainder
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.createSubTerm("
+
taxonomyName
+
", "
+
termName
+
", "
+
remainder
+
")"
);
}
Map
<
String
,
Object
>
properties
=
parsePayload
(
body
);
String
[]
pathTokens
=
remainder
.
split
(
"/"
);
validateName
(
pathTokens
[
pathTokens
.
length
-
1
]);
validateName
(
pathTokens
[
pathTokens
.
length
-
1
]);
properties
.
put
(
"termPath"
,
new
TermPath
(
taxonomyName
,
String
.
format
(
"%s%s"
,
termName
,
remainder
.
replaceAll
(
"/?terms/?([.]*)"
,
"$1."
))));
createResource
(
termResourceProvider
,
new
InstanceRequest
(
properties
));
return
Response
.
status
(
Response
.
Status
.
CREATED
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
201
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@PUT
...
...
@@ -233,6 +317,11 @@ public class TaxonomyService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.updateTerm("
+
taxonomyName
+
", "
+
termName
+
")"
);
}
Map
<
String
,
Object
>
queryProperties
=
new
HashMap
<>();
queryProperties
.
put
(
"termPath"
,
new
TermPath
(
taxonomyName
,
termName
));
...
...
@@ -242,6 +331,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@PUT
...
...
@@ -253,6 +345,11 @@ public class TaxonomyService extends BaseService {
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
,
@PathParam
(
"remainder"
)
String
remainder
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.updateSubTerm("
+
taxonomyName
+
", "
+
termName
+
", "
+
remainder
+
")"
);
}
Map
<
String
,
Object
>
queryProperties
=
new
HashMap
<>();
queryProperties
.
put
(
"termPath"
,
new
TermPath
(
taxonomyName
,
String
.
format
(
"%s%s"
,
termName
,
...
...
@@ -263,6 +360,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@DELETE
...
...
@@ -272,6 +372,11 @@ public class TaxonomyService extends BaseService {
@Context
UriInfo
ui
,
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.deleteTerm("
+
taxonomyName
+
", "
+
termName
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"termPath"
,
new
TermPath
(
taxonomyName
,
termName
));
...
...
@@ -279,6 +384,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
@DELETE
...
...
@@ -289,6 +397,11 @@ public class TaxonomyService extends BaseService {
@PathParam
(
"taxonomyName"
)
String
taxonomyName
,
@PathParam
(
"termName"
)
String
termName
,
@PathParam
(
"remainder"
)
String
remainder
)
throws
CatalogException
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TaxonomyService.deleteSubTerm("
+
taxonomyName
+
", "
+
termName
+
", "
+
remainder
+
")"
);
}
Map
<
String
,
Object
>
properties
=
new
HashMap
<>();
properties
.
put
(
"termPath"
,
new
TermPath
(
taxonomyName
,
String
.
format
(
"%s%s"
,
termName
,
...
...
@@ -297,6 +410,9 @@ public class TaxonomyService extends BaseService {
return
Response
.
status
(
Response
.
Status
.
OK
).
entity
(
new
Results
(
ui
.
getRequestUri
().
toString
(),
200
)).
build
();
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
protected
ResourceProvider
createTaxonomyResourceProvider
(
AtlasTypeSystem
typeSystem
)
{
...
...
webapp/src/main/java/org/apache/atlas/web/resources/TypesResource.java
View file @
bff013f0
...
...
@@ -24,6 +24,7 @@ import org.apache.atlas.AtlasException;
import
org.apache.atlas.services.MetadataService
;
import
org.apache.atlas.typesystem.exception.TypeExistsException
;
import
org.apache.atlas.typesystem.types.DataTypes
;
import
org.apache.atlas.utils.AtlasPerfTracer
;
import
org.apache.atlas.web.util.Servlets
;
import
org.codehaus.jettison.json.JSONArray
;
import
org.codehaus.jettison.json.JSONException
;
...
...
@@ -62,6 +63,7 @@ import java.util.List;
public
class
TypesResource
{
private
static
final
Logger
LOG
=
LoggerFactory
.
getLogger
(
TypesResource
.
class
);
private
static
final
Logger
PERF_LOG
=
AtlasPerfTracer
.
getPerfLogger
(
"rest.TypesResource"
);
private
final
MetadataService
metadataService
;
...
...
@@ -80,7 +82,12 @@ public class TypesResource {
@Consumes
({
Servlets
.
JSON_MEDIA_TYPE
,
MediaType
.
APPLICATION_JSON
})
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
submit
(
@Context
HttpServletRequest
request
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TypesResource.submit()"
);
}
final
String
typeDefinition
=
Servlets
.
getRequestPayload
(
request
);
LOG
.
info
(
"Creating type with definition {} "
,
typeDefinition
);
...
...
@@ -108,6 +115,8 @@ public class TypesResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to persist types"
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -124,7 +133,12 @@ public class TypesResource {
@Consumes
({
Servlets
.
JSON_MEDIA_TYPE
,
MediaType
.
APPLICATION_JSON
})
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
update
(
@Context
HttpServletRequest
request
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TypesResource.update()"
);
}
final
String
typeDefinition
=
Servlets
.
getRequestPayload
(
request
);
LOG
.
info
(
"Updating type with definition {} "
,
typeDefinition
);
...
...
@@ -152,6 +166,8 @@ public class TypesResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to persist types"
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -164,7 +180,12 @@ public class TypesResource {
@Path
(
"{typeName}"
)
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getDefinition
(
@Context
HttpServletRequest
request
,
@PathParam
(
"typeName"
)
String
typeName
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TypesResource.getDefinition("
+
typeName
+
")"
);
}
final
String
typeDefinition
=
metadataService
.
getTypeDefinition
(
typeName
);
JSONObject
response
=
new
JSONObject
();
...
...
@@ -182,6 +203,8 @@ public class TypesResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get type definition for type {}"
,
typeName
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
...
...
@@ -197,7 +220,12 @@ public class TypesResource {
@Produces
(
Servlets
.
JSON_MEDIA_TYPE
)
public
Response
getTypesByFilter
(
@Context
HttpServletRequest
request
,
@DefaultValue
(
TYPE_ALL
)
@QueryParam
(
"type"
)
String
type
)
{
AtlasPerfTracer
perf
=
null
;
try
{
if
(
AtlasPerfTracer
.
isPerfTraceEnabled
(
PERF_LOG
))
{
perf
=
AtlasPerfTracer
.
getPerfTracer
(
PERF_LOG
,
"TypesResource.getTypesByFilter("
+
type
+
")"
);
}
List
<
String
>
result
;
if
(
TYPE_ALL
.
equals
(
type
))
{
result
=
metadataService
.
getTypeNamesList
();
...
...
@@ -219,6 +247,8 @@ public class TypesResource {
}
catch
(
Throwable
e
)
{
LOG
.
error
(
"Unable to get types list"
,
e
);
throw
new
WebApplicationException
(
Servlets
.
getErrorResponse
(
e
,
Response
.
Status
.
INTERNAL_SERVER_ERROR
));
}
finally
{
AtlasPerfTracer
.
log
(
perf
);
}
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment