Skip to content

Commit

Permalink
Move api key injection from client to grafana backend.
Browse files Browse the repository at this point in the history
This change requires plugin conversion from datasource to app. But this
is more secure way to send request - now api key hidden from client,
issue #4
  • Loading branch information
alexanderzobnin committed Jan 18, 2017
1 parent 8137c9c commit a1dc1ab
Show file tree
Hide file tree
Showing 46 changed files with 1,117 additions and 116 deletions.
23 changes: 23 additions & 0 deletions dist/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# New Relic APM Datasource - Custom Plugin
This is a simple datasource for use with the New Relic APM API.

## Security Information
This data source should not be used over http or if you may have malicious authorized users.
Updates are in progres to add an option for proxying requests to NR to increase the security of this plugin.

## Supported Version Information
This datasource has only been tested with Grafana Version 3.0.0-beta7 and 3.0.1 stable and higher.

##To install and use

1. Add the contents of this repository to your grafana plugins directory (default /var/lib/grafana/plugins) and then restart the grafana server.

2. Create a new datasource and select NewRelic from the drop down. You will need your Application ID, and API Key for the NewRelic API.

3. Create a new panel and set the datasource to NewRelic. Metrics take a namespace and optional value configuration. The namespaces must be exact match of the metric name, which can be found for your application [here](https://rpm.newrelic.com/api/explore/applications/metric_names)

This datasource supports aliases and altering the group by interval.
![Alias](http://i.imgur.com/sV0bEoA.png)

If you leave the value field blank, you will get a separate group for each value of the metric. You can access the value as $value in the alias.

13 changes: 13 additions & 0 deletions dist/config/config.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
export declare class NewRelicAppConfigCtrl {
appModel: any;
appEditCtrl: any;
backendSrv: any;
jsonData: any;
apiValidated: boolean;
apiError: boolean;
constructor($scope: any, $injector: any, backendSrv: any);
preUpdate(): Promise<void>;
reset(): void;
validateApiConnection(): any;
static templateUrl: string;
}
24 changes: 24 additions & 0 deletions dist/config/config.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<h3 class="page-heading">New Relic API Credentials</h3>

<div class="gf-form-group">
<div class="gf-form-inline">
<div class="gf-form">
<label class="gf-form-label width-7">API Key</label>
<info-popover mode="right-absolute">
The API key generated for authorization in the APM dashboard.
</info-popover>
<!-- Hidden input to stop chrome from autofilling -->
<input style="display:none;" type="password" name="anotherfakename" />
<input type="password" class="gf-form-input width-20" ng-model="ctrl.appModel.secureJsonData.apiKey" ng-if="!ctrl.appModel.jsonData.tokenSet" placeholder="api key"/>
</div>
<div ng-if="ctrl.appModel.jsonData.tokenSet" class="gf-form">
<input type="text" class="gf-form-input width-20" disabled="disabled" value="saved" />
<div ng-if="ctrl.appModel.enabled">
<i class="fa fa-exclamation-triangle" ng-if="!ctrl.apiValidated" alt="Could not validate api Token."></i>
</div>
</div>
<div class="gf-form">
<a class="btn btn-danger" href="#" ng-click="ctrl.reset()" ng-if="ctrl.appModel.jsonData.tokenSet">reset</a>
</div>
</div>
</div>
50 changes: 50 additions & 0 deletions dist/config/config.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions dist/config/config.js.map

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

52 changes: 52 additions & 0 deletions dist/config/config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
export class NewRelicAppConfigCtrl {
appModel: any;
appEditCtrl: any;
backendSrv: any;
jsonData: any;
apiValidated: boolean;
apiError: boolean;

constructor($scope, $injector, backendSrv) {
this.backendSrv = backendSrv;
console.log(this);

this.appEditCtrl.setPreUpdateHook(this.preUpdate.bind(this));

if (!this.appModel.jsonData) {
this.appModel.jsonData = {};
}
if (!this.appModel.secureJsonData) {
this.appModel.secureJsonData = {};
}

if (this.appModel.enabled && this.appModel.jsonData.tokenSet) {
this.validateApiConnection();
}
}

preUpdate() {
if (this.appModel.secureJsonData.apiKey) {
this.appModel.jsonData.tokenSet = true;
}
return Promise.resolve();
}

reset() {
this.appModel.jsonData.tokenSet = false;
this.appModel.secureJsonData = {};
this.apiValidated = false;
}

validateApiConnection() {
var promise = this.backendSrv.get('/api/plugin-proxy/newrelic-app/v2/applications.json');
promise.then(() => {
this.apiValidated = true;
}, () => {
this.apiValidated = false;
this.apiError = true;
});
return promise;
}

static templateUrl = 'config/config.html';
}
1 change: 0 additions & 1 deletion dist/datasource.js.map

This file was deleted.

3 changes: 2 additions & 1 deletion dist/datasource.d.ts → dist/datasource/datasource.d.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
/// <reference path="../typings/tsd.d.ts" />
/// <reference path="../../src/typings/tsd.d.ts" />
declare class NewRelicDatasource {
private $q;
private backendSrv;
Expand All @@ -7,6 +7,7 @@ declare class NewRelicDatasource {
appId: any;
apiKey: any;
apiUrl: string;
baseUrl: string;
/** @ngInject */
constructor(instanceSettings: any, $q: any, backendSrv: any, templateSrv: any);
query(options: any): any;
Expand Down
15 changes: 8 additions & 7 deletions dist/datasource.js → dist/datasource/datasource.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit a1dc1ab

Please sign in to comment.