Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

DataDog Dashboards #47

Draft
wants to merge 14 commits into
base: develop
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions gradle-metric-schema/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ apply from: "$rootDir/gradle/publish-jar.gradle"

dependencies {
implementation project(':metric-schema-java')
implementation project(':metric-schema-datadog')
implementation project(':metric-schema-grafana')
implementation project(':metric-schema-markdown')
implementation project(':metric-schema-api:metric-schema-api-objects')
implementation 'com.google.guava:guava'
Expand Down Expand Up @@ -34,6 +36,10 @@ pluginBundle {
id = 'com.palantir.metric-schema-markdown'
displayName = "Metric Schema Markdown Plugin"
}
metricSchemaDashboardPlugin {
id = 'com.palantir.metric-schema-dashboard'
displayName = "Metric Schema Dashboard Plugin"
}
}
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
/*
* (c) Copyright 2019 Palantir Technologies Inc. All rights reserved.
*
* Licensed 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 com.palantir.metric.schema.gradle;

import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.fasterxml.jackson.datatype.jdk8.Jdk8Module;
import com.palantir.metric.schema.Dashboard;
import com.palantir.metric.schema.MetricSchema;
import java.io.File;
import java.io.IOException;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import org.gradle.api.DefaultTask;
import org.gradle.api.GradleException;
import org.gradle.api.file.DirectoryProperty;
import org.gradle.api.file.RegularFileProperty;
import org.gradle.api.tasks.InputFile;
import org.gradle.api.tasks.OutputDirectory;
import org.gradle.api.tasks.TaskAction;
import org.gradle.util.GFileUtils;

public abstract class AbstractDashboardTask extends DefaultTask {

private static final ObjectMapper json = new ObjectMapper()
.registerModule(new Jdk8Module())
.enable(SerializationFeature.INDENT_OUTPUT);

private final RegularFileProperty manifestFile = getProject().getObjects().fileProperty();
private final DirectoryProperty outputDirectory = getProject().getObjects().directoryProperty();

@InputFile
public final RegularFileProperty getManifestFile() {
return manifestFile;
}

@OutputDirectory
public final DirectoryProperty getOutputDirectory() {
return outputDirectory;
}

@TaskAction
public final void generate() throws IOException {
File manifest = getManifestFile().getAsFile().get();
Map<String, List<MetricSchema>> schemas = CreateMetricsManifestTask.mapper
.readValue(manifest, new TypeReference<Map<String, List<MetricSchema>>>() {});
if (schemas.isEmpty()) {
return;
}

schemas.values().stream()
.flatMap(Collection::stream)
.flatMap(metricSchema -> metricSchema.getDashboards().entrySet().stream())
.forEach(entry -> {
try {
GFileUtils.mkdirs(getOutputDirectory().getAsFile().get());
json.writeValue(
getOutputDirectory().file(entry.getKey() + "." + dashboardExtension())
.get()
.getAsFile(),
renderDashboard(entry.getValue()));
} catch (IOException e) {
throw new GradleException("Failed to render dashboard to file", e);
}
});
}

protected abstract String dashboardExtension();

protected abstract Object renderDashboard(Dashboard dashboard);

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
/*
* (c) Copyright 2019 Palantir Technologies Inc. All rights reserved.
*
* Licensed 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 com.palantir.metric.schema.gradle;

import com.palantir.metric.schema.Dashboard;
import com.palantir.metric.schema.datadog.DataDogRenderer;
import org.gradle.api.tasks.CacheableTask;

@CacheableTask
public class DataDogDashboardTask extends AbstractDashboardTask {

@Override
protected final String dashboardExtension() {
return "datadog.json";
}

@Override
protected final Object renderDashboard(Dashboard dashboard) {
return DataDogRenderer.render(dashboard);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
/*
* (c) Copyright 2019 Palantir Technologies Inc. All rights reserved.
*
* Licensed 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 com.palantir.metric.schema.gradle;

import com.palantir.metric.schema.Dashboard;
import com.palantir.metric.schema.grafana.GrafanaRenderer;
import org.gradle.api.tasks.CacheableTask;

@CacheableTask
public class GrafanaDashboardTask extends AbstractDashboardTask {

@Override
protected final String dashboardExtension() {
return "grafana.json";
}

@Override
protected final Object renderDashboard(Dashboard dashboard) {
return GrafanaRenderer.render(dashboard);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
/*
* (c) Copyright 2019 Palantir Technologies Inc. All rights reserved.
*
* Licensed 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 com.palantir.metric.schema.gradle;

import org.gradle.api.Plugin;
import org.gradle.api.Project;
import org.gradle.api.file.Directory;
import org.gradle.api.provider.Provider;
import org.gradle.api.tasks.TaskProvider;
import org.gradle.language.base.plugins.LifecycleBasePlugin;

public final class MetricSchemaDashboardPlugin implements Plugin<Project> {

public static final String TASK_GENERATE_DASHBOARDS = "generateDashboards";
public static final String TASK_GENERATE_DASHBOARD_DATADOG = "generateDashboardDataDog";
public static final String TASK_GENERATE_DASHBOARD_GRAFANA = "generateDashboardGrafana";

@Override
public void apply(Project project) {
project.getPluginManager().apply(LifecycleBasePlugin.class);
project.getPluginManager().apply(MetricSchemaPlugin.class);

TaskProvider<CreateMetricsManifestTask> createMetricsManifest =
project.getTasks().named(MetricSchemaPlugin.CREATE_METRICS_MANIFEST, CreateMetricsManifestTask.class);

Provider<Directory> dashboardDir = project.getLayout().getBuildDirectory().dir("dashboards");
TaskProvider<DataDogDashboardTask> datadog = project.getTasks()
.register(TASK_GENERATE_DASHBOARD_DATADOG, DataDogDashboardTask.class, task -> {
task.getManifestFile().set(createMetricsManifest.flatMap(CreateMetricsManifestTask::getOutputFile));
task.getOutputDirectory().set(dashboardDir);
task.dependsOn(createMetricsManifest);
});

TaskProvider<GrafanaDashboardTask> grafana = project.getTasks()
.register(TASK_GENERATE_DASHBOARD_GRAFANA, GrafanaDashboardTask.class, task -> {
task.getManifestFile().set(createMetricsManifest.flatMap(CreateMetricsManifestTask::getOutputFile));
task.getOutputDirectory().set(dashboardDir);
task.dependsOn(createMetricsManifest);
});

project.getTasks().register(TASK_GENERATE_DASHBOARDS, task -> {
task.dependsOn(datadog);
task.dependsOn(grafana);
});
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@

public final class MetricSchemaMarkdownPlugin implements Plugin<Project> {

public static final String GENERATE_METRICS_MARKDOWN = "generateMetricsMarkdown";

@Override
public void apply(Project project) {
project.getPluginManager().apply(LifecycleBasePlugin.class);
Expand All @@ -35,7 +37,7 @@ public void apply(Project project) {
project.getTasks().named(MetricSchemaPlugin.CREATE_METRICS_MANIFEST, CreateMetricsManifestTask.class);

TaskProvider<GenerateMetricMarkdownTask> generateMetricsMarkdown = project.getTasks()
.register(MetricSchemaPlugin.GENERATE_METRICS_MARKDOWN, GenerateMetricMarkdownTask.class, task -> {
.register(GENERATE_METRICS_MARKDOWN, GenerateMetricMarkdownTask.class, task -> {
task.getManifestFile().set(createMetricsManifest.flatMap(CreateMetricsManifestTask::getOutputFile));
task.outputFile().set(project.file("metrics.md"));
task.dependsOn(createMetricsManifest);
Expand All @@ -44,11 +46,10 @@ public void apply(Project project) {

// Wire up dependencies so running `./gradlew --write-locks` will update the markdown
StartParameter startParam = project.getGradle().getStartParameter();
if (startParam.isWriteDependencyLocks()
&& !startParam.getTaskNames().contains(MetricSchemaPlugin.GENERATE_METRICS_MARKDOWN)) {
if (startParam.isWriteDependencyLocks() && !startParam.getTaskNames().contains(GENERATE_METRICS_MARKDOWN)) {
List<String> taskNames = ImmutableList.<String>builder()
.addAll(startParam.getTaskNames())
.add(MetricSchemaPlugin.GENERATE_METRICS_MARKDOWN)
.add(GENERATE_METRICS_MARKDOWN)
.build();
startParam.setTaskNames(taskNames);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,6 @@ public final class MetricSchemaPlugin implements Plugin<Project> {
public static final String METRIC_SCHEMA_RESOURCE = "metric-schema/metrics.json";

public static final String COMPILE_METRIC_SCHEMA = "compileMetricSchema";
public static final String GENERATE_METRICS_MARKDOWN = "generateMetricsMarkdown";
public static final String CREATE_METRICS_MANIFEST = "createMetricsManifest";

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
implementation-class=com.palantir.metric.schema.gradle.MetricSchemaDashboardPlugin
6 changes: 6 additions & 0 deletions metric-schema-api/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

apply plugin: 'com.palantir.conjure'
apply plugin: 'com.palantir.conjure-publish'
apply from: "$rootDir/gradle/publish-jar.gradle"

conjure {
java {
Expand All @@ -26,3 +27,8 @@ conjure {
configure(subprojects) {
apply from: "$rootDir/gradle/publish-jar.gradle"
}

dependencies {
api project('metric-schema-api-objects')
implementation 'com.google.guava:guava'
}
51 changes: 50 additions & 1 deletion metric-schema-api/src/main/conjure/metric-schema-api.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,23 +2,32 @@ types:
definitions:
default-package: com.palantir.metric.schema
objects:

MetricSchema:
fields:
namespaces: map<string, MetricNamespace>
dashboards:
docs: Set of dashboards to be produced from this project.
type: map<string, Dashboard>
providedDashboardRows:
docs: Set of dashboard rows to be inherited by consumers of this project.
type: list<Row>
options:
docs: >
Additional pieces of information that do not change the overall declaration,
but may affect the way it is handled in a particular context. For example,
`javaPackage` will determine the package of the generated classes.
type: map<string, string>

MetricNamespace:
fields:
shortName:
docs: A short name describing the metrics. Used to construct the name of the generated utility class.
type: optional<string>
docs: Documentation
metrics:
type: map<string,MetricDefinition>
type: map<string, MetricDefinition>

MetricDefinition:
fields:
type: MetricType
Expand All @@ -31,6 +40,46 @@ types:
- METER
- TIMER
- HISTOGRAM

Dashboard:
fields:
title: string
selectedTags: map<string, string>
templatedTags: list<string>
rows: list<Row>
Row:
fields:
title: string
cells: list<Cell>
Cell:
fields:
title: string
content: CellContent
CellContent:
union:
timeseries: TimeseriesCell

TimeseriesCell:
fields:
series: list<Timeseries>

Timeseries:
fields:
metric: string
aggregation: Aggregation
Aggregation:
fields:
function: AggregationFunction
groupBy:
docs: The set of tags to group by.
type: set<string>
AggregationFunction:
values:
- AVG
- SUM
- MIN
- MAX

Documentation:
docs: Documentation describing an associated component. Markdown syntax may be used.
alias: string
Loading