[GRIFFIN-244] get metrics by instance
This is just a squashed version of #491
Author: Rodion Gorkovenko <rodiongork@github.com>
Author: rodion <dershov@griddynamics.com>
Closes #492 from RodionGork/griffin-244-squashed.
diff --git a/griffin-doc/service/api-guide.md b/griffin-doc/service/api-guide.md
index 95113af..17bca5b 100644
--- a/griffin-doc/service/api-guide.md
+++ b/griffin-doc/service/api-guide.md
@@ -42,12 +42,14 @@
- [Get Job Instances](#34)
- [Get Job Healthy Statistics](#35)
- [Download Sample Records](#36)
+ - [Get Job Instance by Id](#38)
- [Metrics](#4)
- [Get Metrics](#41)
- [Add Metric Value](#42)
- [Get Metric Value](#43)
- [Remove Metric Value](#44)
+ - [Get Metric Value by Job Instance Id](#45)
- [Hive MetaStore](#5)
- [Get Table Metadata](#51)
@@ -747,6 +749,17 @@
```
If successful, this method returns missing records in the response body, maximum record count is 100.
+<div id = "38"></div>
+
+### Get Job Instance by Id
+`GET /api/v1/jobs/instances/{jobInstanceId}`
+
+#### API Example
+```
+curl -k -G -X GET http://127.0.0.1:8080/api/v1/jobs/instances/1
+```
+If successful, this method returns job instance description for the given job instance id. If there is no instance with given id found, returns Griffin Exception.
+
<h2 id = "4"></h2>
## Metrics
@@ -927,6 +940,32 @@
}
```
+<div id = "45"></div>
+
+### Get Metric Value by Job Instance Id
+`GET http://127.0.0.1:8080/api/v1/metrics/values/:jobInstanceId`
+#### API Example
+```
+curl -k -G -X GET http://127.0.0.1:8080/api/v1/metrics/values/{304}
+{
+ "name": "some_job",
+ "tmst": 1553526960000,
+ "value": {
+ "total": 74,
+ "miss": 31,
+ "matched": 43,
+ "matchedFraction": 0.581081081081081
+ },
+ "metadata": {
+ "applicationId": "\"application_1549876136110_0237\"",
+ }
+}
+```
+
+
+
+
+
<h2 id = "5"></h2>
### Hive MetaStore
diff --git a/griffin-doc/service/postman/griffin.json b/griffin-doc/service/postman/griffin.json
index e789121..55d7bac 100644
--- a/griffin-doc/service/postman/griffin.json
+++ b/griffin-doc/service/postman/griffin.json
@@ -1406,7 +1406,7 @@
"health"
]
},
- "description": "`GET /api/v1/jobs/health`\n\n#### Response Body Sample\n```\n{\n \"healthyJobCount\": 1,\n \"jobCount\": 2\n}\n```"
+ "description": "`GET /api/v1/jobs/health`\n\n#### Response Body Sample\n```\n{\n \"job instance info\"\n}\n```"
},
"response": [
{
@@ -1430,7 +1430,7 @@
"health"
]
},
- "description": "`GET /api/v1/jobs/health`\n\n#### Response Body Sample\n```\n{\n \"healthyJobCount\": 1,\n \"jobCount\": 2\n}\n```"
+ "description": "`GET /api/v1/jobs/health`\n\n#### Response Body Sample\n```\n{\n \"job instance info\"\n}\n```"
},
"status": "OK",
"code": 200,
@@ -1838,6 +1838,75 @@
"body": ""
}
]
+ },
+ {
+ "name": "Get Job Instance by Id",
+ "request": {
+ "method": "GET",
+ "header": [],
+ "body": {
+ "mode": "raw",
+ "raw": ""
+ },
+ "url": {
+ "raw": "{{BASE_PATH}}/api/v1/jobs/instances/:id",
+ "host": [
+ "{{BASE_PATH}}"
+ ],
+ "path": [
+ "api",
+ "v1",
+ "jobs",
+ "instances",
+ ":id"
+ ],
+ "variable": [
+ {
+ "key": "id",
+ "value": "2"
+ }
+ ]
+ },
+ "description": "`GET /api/v1/jobs/instances/{id}`\n\n#### Response Body Sample\n```\n{\n \"job instance info\"\n}\n```"
+ },
+ "response": [
+ {
+ "name": "Get Job Instance by Id",
+ "originalRequest": {
+ "method": "GET",
+ "header": [],
+ "body": {
+ "mode": "raw",
+ "raw": ""
+ },
+ "url": {
+ "raw": "{{BASE_PATH}}/api/v1/jobs/instances/:id",
+ "host": [
+ "{{BASE_PATH}}"
+ ],
+ "path": [
+ "api",
+ "v1",
+ "jobs",
+ "instances",
+ ":id"
+ ],
+ "variable": [
+ {
+ "key": "id",
+ "value": "2"
+ }
+ ]
+ },
+ "description": "`GET /api/v1/jobs/instances/{id}`\n\n#### Response Body Sample\n```\n{\n \"job instance info\"\n}\n```"
+ },
+ "status": "OK",
+ "code": 200,
+ "_postman_previewlanguage": "json",
+ "cookie": [],
+ "body": "{\n \"healthyJobCount\": 1,\n \"jobCount\": 2\n}"
+ }
+ ]
}
]
},
@@ -2080,7 +2149,7 @@
],
"body": {
"mode": "raw",
- "raw": "[\n\t{\n\t\t\"name\" : \"metricName\",\n\t\t\"tmst\" : 1509599811123,\n\t\t\"value\" : {\n\t\t\t\"__tmst\" : 1509599811123,\n\t\t\t\"miss\" : 11,\n\t\t\t\"total\" : 125000,\n\t\t\t\"matched\" : 124989\n\t\t}\n }\n]"
+ "raw": "[\n\t{\n\t\t\"name\" : \"metricName\",\n\t\t\"tmst\" : 1509599811123,\n\t\t\"applicationId\" : \"app_1\",\n\t\t\"value\" : {\n\t\t\t\"__tmst\" : 1509599811123,\n\t\t\t\"miss\" : 11,\n\t\t\t\"total\" : 125000,\n\t\t\t\"matched\" : 124989\n\t\t}\n }\n]"
},
"url": {
"raw": "{{BASE_PATH}}/api/v1/metrics/values",
@@ -2109,7 +2178,7 @@
],
"body": {
"mode": "raw",
- "raw": "[\n\t{\n\t\t\"name\" : \"metricName\",\n\t\t\"tmst\" : 1509599811123,\n\t\t\"value\" : {\n\t\t\t\"__tmst\" : 1509599811123,\n\t\t\t\"miss\" : 11,\n\t\t\t\"total\" : 125000,\n\t\t\t\"matched\" : 124989\n\t\t}\n }\n]"
+ "raw": "[\n\t{\n\t\t\"name\" : \"metricName\",\n\t\t\"tmst\" : 1509599811123,\n\t\t\"applicationId\" : \"app_1\",\n\t\t\"value\" : {\n\t\t\t\"__tmst\" : 1509599811123,\n\t\t\t\"miss\" : 11,\n\t\t\t\"total\" : 125000,\n\t\t\t\"matched\" : 124989\n\t\t}\n }\n]"
},
"url": {
"raw": "{{BASE_PATH}}/api/v1/metrics/values",
@@ -2307,6 +2376,75 @@
"body": "{\"took\":363,\"timed_out\":false,\"total\":5,\"deleted\":5,\"batches\":1,\"version_conflicts\":0,\"noops\":0,\"retries\":{\"bulk\":0,\"search\":0},\"throttled_millis\":0,\"requests_per_second\":-1.0,\"throttled_until_millis\":0,\"failures\":[]}"
}
]
+ },
+ {
+ "name": "Get Metrics Value by Job Instance Id",
+ "request": {
+ "method": "GET",
+ "header": [],
+ "body": {
+ "mode": "raw",
+ "raw": ""
+ },
+ "url": {
+ "raw": "{{BASE_PATH}}/api/v1/metrics/values/:jobInstanceId",
+ "host": [
+ "{{BASE_PATH}}"
+ ],
+ "path": [
+ "api",
+ "v1",
+ "metrics",
+ "values",
+ ":jobInstanceId"
+ ],
+ "variable": [
+ {
+ "key": "jobInstanceId",
+ "value": "304"
+ }
+ ]
+ },
+ "description": "`GET /api/v1/metrics/values/{jobInstanceId}`\n\n#### Response Body Sample\n```\n{\n \"metric value\"\n}\n```"
+ },
+ "response": [
+ {
+ "name": "Get Metrics Value by Job Instance Id",
+ "originalRequest": {
+ "method": "GET",
+ "header": [],
+ "body": {
+ "mode": "raw",
+ "raw": ""
+ },
+ "url": {
+ "raw": "{{BASE_PATH}}/api/v1/metrics/values/:jobInstanceId",
+ "host": [
+ "{{BASE_PATH}}"
+ ],
+ "path": [
+ "api",
+ "v1",
+ "metrics",
+ "values",
+ ":jobInstanceId"
+ ],
+ "variable": [
+ {
+ "key": "jobInstanceId",
+ "value": "304"
+ }
+ ]
+ },
+ "description": "`GET /api/v1/metrics/values/{jobInstanceId}`\n\n#### Response Body Sample\n```\n{\n \"metric value\"\n}\n```"
+ },
+ "status": "OK",
+ "code": 200,
+ "_postman_previewlanguage": "json",
+ "cookie": [],
+ "body": "{\n \"name\": some_job,\n \"tmst\": 1553526960000\n \"applicationId\": application_1549876136110_0237\n \"value\": {\n \"total\": 74}}"
+ }
+ ]
}
]
},
diff --git a/measure/src/main/scala/org/apache/griffin/measure/context/MetricWrapper.scala b/measure/src/main/scala/org/apache/griffin/measure/context/MetricWrapper.scala
index df162a7..484797a 100644
--- a/measure/src/main/scala/org/apache/griffin/measure/context/MetricWrapper.scala
+++ b/measure/src/main/scala/org/apache/griffin/measure/context/MetricWrapper.scala
@@ -28,7 +28,7 @@
val _Name = "name"
val _Timestamp = "tmst"
val _Value = "value"
- val _ApplicationId = "applicationId"
+ val _Metadata = "metadata"
val metrics: MutableMap[Long, Map[String, Any]] = MutableMap()
@@ -47,7 +47,7 @@
(_Name -> name),
(_Timestamp -> timestamp),
(_Value -> value),
- (_ApplicationId -> applicationId)
+ (_Metadata -> Map("applicationId" -> applicationId))
))
}
}
diff --git a/measure/src/test/scala/org/apache/griffin/measure/context/MetricWrapperTest.scala b/measure/src/test/scala/org/apache/griffin/measure/context/MetricWrapperTest.scala
index 8ad7d5d..4a49c75 100644
--- a/measure/src/test/scala/org/apache/griffin/measure/context/MetricWrapperTest.scala
+++ b/measure/src/test/scala/org/apache/griffin/measure/context/MetricWrapperTest.scala
@@ -35,8 +35,9 @@
metricWrapper.insertMetric(2, Map("miss" -> 4))
metricWrapper.flush should be (Map(
1L -> Map("name" -> "test", "tmst" -> 1, "value" -> Map("total" -> 10, "miss"-> 2, "match" -> 8),
- "applicationId" -> "appId"),
- 2L -> Map("name" -> "test", "tmst" -> 2, "value" -> Map("total" -> 20, "miss"-> 4), "applicationId" -> "appId")
+ "metadata" -> Map("applicationId" -> "appId")),
+ 2L -> Map("name" -> "test", "tmst" -> 2, "value" -> Map("total" -> 20, "miss"-> 4),
+ "metadata" -> Map("applicationId" -> "appId"))
))
}
diff --git a/service/src/main/java/org/apache/griffin/core/exception/GriffinExceptionMessage.java b/service/src/main/java/org/apache/griffin/core/exception/GriffinExceptionMessage.java
index 6a9b9da..4f65248 100644
--- a/service/src/main/java/org/apache/griffin/core/exception/GriffinExceptionMessage.java
+++ b/service/src/main/java/org/apache/griffin/core/exception/GriffinExceptionMessage.java
@@ -76,6 +76,8 @@
INSTANCE_ID_DOES_NOT_EXIST(40409, "Instance id does not exist"),
+ JOB_INSTANCE_NOT_FOUND(40410, "No job instances with given job instance id found"),
+
//409, "Conflict"
MEASURE_NAME_ALREADY_EXIST(40901, "Measure name already exists"),
diff --git a/service/src/main/java/org/apache/griffin/core/job/entity/JobInstanceBean.java b/service/src/main/java/org/apache/griffin/core/job/entity/JobInstanceBean.java
index 6fc5cf2..c3b0f1c 100644
--- a/service/src/main/java/org/apache/griffin/core/job/entity/JobInstanceBean.java
+++ b/service/src/main/java/org/apache/griffin/core/job/entity/JobInstanceBean.java
@@ -186,6 +186,13 @@
public JobInstanceBean() {
}
+ public JobInstanceBean(State state, Long tms, Long expireTms, String appId) {
+ this.state = state;
+ this.tms = tms;
+ this.expireTms = expireTms;
+ this.appId=appId;
+ }
+
public JobInstanceBean(State state, Long tms, Long expireTms) {
this.state = state;
this.tms = tms;
diff --git a/service/src/main/java/org/apache/griffin/core/metric/MetricController.java b/service/src/main/java/org/apache/griffin/core/metric/MetricController.java
index 4d39ba3..5cd43af 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/MetricController.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/MetricController.java
@@ -27,6 +27,7 @@
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
+import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
@@ -71,4 +72,9 @@
String metricName) {
return metricService.deleteMetricValues(metricName);
}
+
+ @RequestMapping(value = "/metrics/values/{instanceId}", method = RequestMethod.GET)
+ public MetricValue getMetric(@PathVariable("instanceId") Long id){
+ return metricService.findMetric(id);
+ }
}
diff --git a/service/src/main/java/org/apache/griffin/core/metric/MetricService.java b/service/src/main/java/org/apache/griffin/core/metric/MetricService.java
index 039b0cb..75402ff 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/MetricService.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/MetricService.java
@@ -37,4 +37,6 @@
ResponseEntity addMetricValues(List<MetricValue> values);
ResponseEntity<?> deleteMetricValues(String metricName);
+
+ MetricValue findMetric(Long id);
}
diff --git a/service/src/main/java/org/apache/griffin/core/metric/MetricServiceImpl.java b/service/src/main/java/org/apache/griffin/core/metric/MetricServiceImpl.java
index f817f65..beca19e 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/MetricServiceImpl.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/MetricServiceImpl.java
@@ -23,6 +23,7 @@
import static org.apache.griffin.core.exception.GriffinExceptionMessage.INVALID_METRIC_RECORDS_OFFSET;
import static org.apache.griffin.core.exception.GriffinExceptionMessage.INVALID_METRIC_RECORDS_SIZE;
import static org.apache.griffin.core.exception.GriffinExceptionMessage.INVALID_METRIC_VALUE_FORMAT;
+import static org.apache.griffin.core.exception.GriffinExceptionMessage.JOB_INSTANCE_NOT_FOUND;
import java.io.IOException;
import java.util.ArrayList;
@@ -36,6 +37,8 @@
import org.apache.commons.lang.StringUtils;
import org.apache.griffin.core.exception.GriffinException;
import org.apache.griffin.core.job.entity.AbstractJob;
+import org.apache.griffin.core.job.entity.JobInstanceBean;
+import org.apache.griffin.core.job.repo.JobInstanceRepo;
import org.apache.griffin.core.job.repo.JobRepo;
import org.apache.griffin.core.measure.entity.Measure;
import org.apache.griffin.core.measure.repo.MeasureRepo;
@@ -59,6 +62,8 @@
private JobRepo<AbstractJob> jobRepo;
@Autowired
private MetricStore metricStore;
+ @Autowired
+ private JobInstanceRepo jobInstanceRepo;
@Override
public Map<String, List<Metric>> getAllMetrics() {
@@ -139,6 +144,23 @@
}
}
+ @Override
+ public MetricValue findMetric(Long id) {
+ JobInstanceBean jobInstanceBean = jobInstanceRepo.findByInstanceId(id);
+ if (jobInstanceBean == null){
+ LOGGER.warn("There are no job instances with id {} ", id);
+ throw new GriffinException
+ .NotFoundException(JOB_INSTANCE_NOT_FOUND);
+ }
+ String appId = jobInstanceBean.getAppId();
+ try {
+ return metricStore.getMetric(appId);
+ } catch (IOException e) {
+ LOGGER.warn("Failed to get metric for applicationId {} ", appId);
+ throw new GriffinException.ServiceException("Failed to find metric", e);
+ }
+ }
+
private void checkFormat(MetricValue value) {
if (StringUtils.isBlank(value.getName()) || value.getTmst() == null
|| MapUtils.isEmpty(value.getValue())) {
diff --git a/service/src/main/java/org/apache/griffin/core/metric/MetricStore.java b/service/src/main/java/org/apache/griffin/core/metric/MetricStore.java
index a452648..f85c4db 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/MetricStore.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/MetricStore.java
@@ -34,4 +34,6 @@
throws IOException;
ResponseEntity<?> deleteMetricValues(String metricName) throws IOException;
+
+ MetricValue getMetric(String applicationId) throws IOException;
}
diff --git a/service/src/main/java/org/apache/griffin/core/metric/MetricStoreImpl.java b/service/src/main/java/org/apache/griffin/core/metric/MetricStoreImpl.java
index 3bff8f5..2d577bb 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/MetricStoreImpl.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/MetricStoreImpl.java
@@ -31,7 +31,9 @@
import java.util.HashMap;
import java.util.List;
import java.util.Map;
+import java.util.Objects;
+import org.apache.commons.lang.StringUtils;
import org.apache.griffin.core.metric.model.MetricValue;
import org.apache.griffin.core.util.JsonUtil;
import org.apache.http.Header;
@@ -142,14 +144,16 @@
.hasNonNull("hits")) {
for (JsonNode node : jsonNode.get("hits").get("hits")) {
JsonNode sourceNode = node.get("_source");
- Map<String, Object> value = JsonUtil.toEntity(sourceNode
- .get("value").toString(),
- new TypeReference<Map<String, Object>>() {
- });
- MetricValue metricValue = new MetricValue(sourceNode
- .get("name")
- .asText(),
+ Map<String, Object> value = JsonUtil.toEntity(
+ sourceNode.get("value").toString(),
+ new TypeReference<Map<String, Object>>() {});
+ Map<String, Object> meta = JsonUtil.toEntity(
+ Objects.toString(sourceNode.get("metadata"), null),
+ new TypeReference<Map<String, Object>>() {});
+ MetricValue metricValue = new MetricValue(
+ sourceNode.get("name").asText(),
Long.parseLong(sourceNode.get("tmst").asText()),
+ meta,
value);
metricValues.add(metricValue);
}
@@ -206,4 +210,14 @@
return String.format("Basic %s", Base64.getEncoder().encodeToString(
auth.getBytes()));
}
+
+ @Override
+ public MetricValue getMetric(String applicationId) throws IOException {
+ Response response = client.performRequest(
+ "GET", urlGet,
+ Collections.singletonMap(
+ "q", "metadata.applicationId:" + applicationId));
+ List<MetricValue> metricValues = getMetricValuesFromResponse(response);
+ return metricValues.get(0);
+ }
}
diff --git a/service/src/main/java/org/apache/griffin/core/metric/model/MetricValue.java b/service/src/main/java/org/apache/griffin/core/metric/model/MetricValue.java
index 4839f9f..4c7f386 100644
--- a/service/src/main/java/org/apache/griffin/core/metric/model/MetricValue.java
+++ b/service/src/main/java/org/apache/griffin/core/metric/model/MetricValue.java
@@ -19,7 +19,9 @@
package org.apache.griffin.core.metric.model;
+import java.util.Collections;
import java.util.Map;
+import java.util.Objects;
public class MetricValue {
@@ -27,6 +29,8 @@
private Long tmst;
+ private Map<String, Object> metadata;
+
private Map<String, Object> value;
public MetricValue() {
@@ -36,6 +40,15 @@
this.name = name;
this.tmst = tmst;
this.value = value;
+ this.metadata = Collections.emptyMap();
+ }
+
+
+ public MetricValue(String name, Long tmst, Map<String, Object> metadata, Map<String, Object> value) {
+ this.name = name;
+ this.tmst = tmst;
+ this.metadata = metadata;
+ this.value = value;
}
public String getName() {
@@ -61,4 +74,35 @@
public void setValue(Map<String, Object> value) {
this.value = value;
}
+
+ public Map<String, Object> getMetadata() {
+ return metadata;
+ }
+
+ public void setMetadata(Map<String, Object> metadata) {
+ this.metadata = metadata;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ MetricValue that = (MetricValue) o;
+ return Objects.equals(name, that.name) &&
+ Objects.equals(tmst, that.tmst) &&
+ Objects.equals(metadata, that.metadata) &&
+ Objects.equals(value, that.value);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(name, tmst, metadata, value);
+ }
+
+ @Override
+ public String toString() {
+ return String.format(
+ "MetricValue{name=%s, ts=%s, meta=%s, value=%s}",
+ name, tmst, metadata, value);
+ }
}
diff --git a/service/src/test/java/org/apache/griffin/core/job/JobControllerTest.java b/service/src/test/java/org/apache/griffin/core/job/JobControllerTest.java
index d9d5d80..aa10cf2 100644
--- a/service/src/test/java/org/apache/griffin/core/job/JobControllerTest.java
+++ b/service/src/test/java/org/apache/griffin/core/job/JobControllerTest.java
@@ -38,6 +38,7 @@
import org.apache.griffin.core.exception.GriffinException;
import org.apache.griffin.core.exception.GriffinExceptionHandler;
+import org.apache.griffin.core.exception.GriffinExceptionMessage;
import org.apache.griffin.core.job.entity.AbstractJob;
import org.apache.griffin.core.job.entity.JobHealth;
import org.apache.griffin.core.job.entity.JobInstanceBean;
@@ -186,6 +187,16 @@
}
@Test
+ public void testJobInstanceWithGivenIdNotFound() throws Exception {
+ Long jobInstanceId = 2L;
+ doThrow(new GriffinException.NotFoundException(GriffinExceptionMessage.JOB_INSTANCE_NOT_FOUND))
+ .when(service).findInstance(jobInstanceId);
+
+ mvc.perform(get(URLHelper.API_VERSION_PATH + "/jobs/instances/2"))
+ .andExpect(status().isNotFound());
+ }
+
+ @Test
public void testGetHealthInfo() throws Exception {
JobHealth jobHealth = new JobHealth(1, 3);
given(service.getHealthInfo()).willReturn(jobHealth);
diff --git a/service/src/test/java/org/apache/griffin/core/metric/MetricServiceImplTest.java b/service/src/test/java/org/apache/griffin/core/metric/MetricServiceImplTest.java
index aa55f7a..39837f0 100644
--- a/service/src/test/java/org/apache/griffin/core/metric/MetricServiceImplTest.java
+++ b/service/src/test/java/org/apache/griffin/core/metric/MetricServiceImplTest.java
@@ -33,6 +33,9 @@
import org.apache.griffin.core.exception.GriffinException;
import org.apache.griffin.core.job.entity.AbstractJob;
+import org.apache.griffin.core.job.entity.JobInstanceBean;
+import org.apache.griffin.core.job.entity.LivySessionStates;
+import org.apache.griffin.core.job.repo.JobInstanceRepo;
import org.apache.griffin.core.job.repo.JobRepo;
import org.apache.griffin.core.measure.entity.Measure;
import org.apache.griffin.core.measure.repo.MeasureRepo;
@@ -63,6 +66,8 @@
private JobRepo<AbstractJob> jobRepo;
@Mock
private MetricStoreImpl metricStore;
+ @Mock
+ private JobInstanceRepo jobInstanceRepo;
@Autowired
private Environment env;
@@ -204,4 +209,43 @@
}
+ @Test
+ public void testFindMetricSuccess() throws IOException {
+ Long id = 1L;
+ String appId = "application";
+ MetricValue expectedMetric = new MetricValue(
+ "name", 1234L, Collections.singletonMap("applicationId", appId), new HashMap<>());
+
+ given(jobInstanceRepo.findByInstanceId(id))
+ .willReturn(new JobInstanceBean(LivySessionStates.State.RUNNING, 12L, 32L, appId));
+ given(metricStore.getMetric(appId))
+ .willReturn(expectedMetric);
+ MetricValue actualMetric = service.findMetric(id);
+
+ assertEquals(expectedMetric, actualMetric);
+ }
+
+ @Test(expected = GriffinException.NotFoundException.class)
+ public void testFailedToFindJobInstance() throws IOException {
+ Long id = 1L;
+ given(jobInstanceRepo.findByInstanceId(id))
+ .willReturn(null);
+ service.findMetric(id);
+
+ }
+
+ @Test(expected = GriffinException.ServiceException.class)
+ public void testFindMetricFailure() throws IOException {
+ Long id = 1L;
+ String appId = "application";
+
+ given(jobInstanceRepo.findByInstanceId(id))
+ .willReturn(new JobInstanceBean(LivySessionStates.State.RUNNING, 12L, 32L, appId));
+ given(metricStore.getMetric(appId))
+ .willThrow(new GriffinException.ServiceException("", new RuntimeException()));
+ service.findMetric(id);
+
+ }
+
+
}
diff --git a/service/src/test/java/org/apache/griffin/core/metric/MetricStoreImplTest.java b/service/src/test/java/org/apache/griffin/core/metric/MetricStoreImplTest.java
index d3cbfb0..b91f6ba 100644
--- a/service/src/test/java/org/apache/griffin/core/metric/MetricStoreImplTest.java
+++ b/service/src/test/java/org/apache/griffin/core/metric/MetricStoreImplTest.java
@@ -19,15 +19,55 @@
package org.apache.griffin.core.metric;
-import static org.junit.Assert.assertTrue;
+import org.apache.griffin.core.metric.model.MetricValue;
+import org.apache.http.HttpEntity;
+import org.elasticsearch.client.Response;
+import org.elasticsearch.client.RestClient;
+import org.elasticsearch.client.RestClientBuilder;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.powermock.api.mockito.PowerMockito;
+import org.powermock.core.classloader.annotations.PowerMockIgnore;
+import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.powermock.modules.junit4.PowerMockRunner;
+import java.io.IOException;
+import java.io.InputStream;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
+import java.net.URISyntaxException;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
-import org.junit.Test;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.BDDMockito.*;
+@RunWith(PowerMockRunner.class)
+@PrepareForTest({RestClient.class, RestClientBuilder.class})
+@PowerMockIgnore("javax.management.*")
public class MetricStoreImplTest {
+ private static final String INDEX = "griffin";
+ private static final String TYPE = "accuracy";
+
+ private static final String urlBase = String.format("/%s/%s", INDEX, TYPE);
+ private static final String urlGet = urlBase.concat("/_search?filter_path=hits.hits._source");
+
+ private RestClient restClientMock;
+
+ @Before
+ public void setup(){
+ PowerMockito.mockStatic(RestClient.class);
+ restClientMock = PowerMockito.mock(RestClient.class);
+ RestClientBuilder restClientBuilderMock = PowerMockito.mock(RestClientBuilder.class);
+
+ given(RestClient.builder(anyVararg())).willReturn(restClientBuilderMock);
+ given(restClientBuilderMock.build()).willReturn(restClientMock);
+ }
+
@Test
public void testBuildBasicAuthString()
throws NoSuchMethodException, InvocationTargetException,
@@ -40,4 +80,39 @@
assertTrue(authStr.equals("Basic dXNlcjpwYXNzd29yZA=="));
}
+ @Test
+ public void testMetricGetting() throws IOException, URISyntaxException {
+ //given
+ Response responseMock = PowerMockito.mock(Response.class);
+ HttpEntity httpEntityMock = PowerMockito.mock(HttpEntity.class);
+ InputStream is = Thread.currentThread().getContextClassLoader()
+ .getResourceAsStream("metricvalue.json");
+ Map<String, String> map = new HashMap<>();
+ map.put("q", "metadata.applicationId:application_1549876136110_0018");
+
+ Map<String, Object> value = new HashMap<String, Object>(){{
+ put("total", 74);
+ put("miss", 0);
+ put("matched", 74);
+ put("matchedFraction", 1);
+ }};
+ MetricValue expectedMetric = new MetricValue("de_demo_results_comparision",
+ 1549985089648L,
+ Collections.singletonMap("applicationId", "application_1549876136110_0018"),
+ value);
+
+
+ given(restClientMock.performRequest(eq("GET"), eq(urlGet), eq(map), anyVararg())).willReturn(responseMock);
+ given(responseMock.getEntity()).willReturn(httpEntityMock);
+ given(httpEntityMock.getContent()).willReturn(is);
+
+ //when
+ MetricStoreImpl metricStore = new MetricStoreImpl("", 0, "", "", "");
+ MetricValue metric = metricStore.getMetric("application_1549876136110_0018");
+
+ //then
+ PowerMockito.verifyStatic();
+ assertEquals(expectedMetric, metric);
+ }
+
}
diff --git a/service/src/test/resources/metricvalue.json b/service/src/test/resources/metricvalue.json
new file mode 100644
index 0000000..690c1c4
--- /dev/null
+++ b/service/src/test/resources/metricvalue.json
@@ -0,0 +1,51 @@
+{
+ "took": 47,
+ "timed_out": false,
+ "_shards": {
+ "total": 5,
+ "successful": 5,
+ "skipped": 0,
+ "failed": 0
+ },
+ "hits": {
+ "total": 17,
+ "max_score": 3.226844,
+ "hits": [
+ {
+ "_index": "griffin",
+ "_type": "accuracy",
+ "_id": "RZFP4mgBkZqzqlKSwWtJ",
+ "_score": 3.226844,
+ "_source": {
+ "name": "de_demo_results_comparision",
+ "tmst": 1549985089648,
+ "value": {
+ "total": 74,
+ "miss": 0,
+ "matched": 74,
+ "matchedFraction": 1
+ },
+ "metadata": {
+ "applicationId": "application_1549876136110_0018"
+ }
+ }
+ },
+ {
+ "_index": "griffin",
+ "_type": "accuracy",
+ "_id": "taMpvmgBfOpRJiYFj5Xg",
+ "_score": 2.4107988,
+ "_source": {
+ "name": "de_demo_results_comparision",
+ "tmst": 1549378607658,
+ "value": {
+ "total": 74,
+ "miss": 0,
+ "matched": 74,
+ "matchedFraction": 1
+ }
+ }
+ }
+ ]
+ }
+}
\ No newline at end of file