grafana/public/app/features/manage-dashboards/DashboardImportCtrl.ts

259 lines
6.3 KiB
TypeScript
Raw Normal View History

2017-12-20 05:33:33 -06:00
import _ from 'lodash';
import config from 'app/core/config';
2018-09-05 05:09:16 -05:00
import locationUtil from 'app/core/utils/location_util';
import { ValidationSrv } from './services/ValidationSrv';
import { NavModelSrv } from 'app/core/core';
import { ILocationService, IScope } from 'angular';
Chore: Remove angular dependency from backendSrv (#20999) * Chore: Remove angular dependency from backendSrv * Refactor: Naive soultion for logging out unauthorized users * Refactor: Restructures to different streams * Refactor: Restructures datasourceRequest * Refactor: Flipped back if statement * Refactor: Extracted getFromFetchStream * Refactor: Extracts toFailureStream operation * Refactor: Fixes issue when options.params contains arrays * Refactor: Fixes broken test (but we need a lot more) * Refactor: Adds explaining comments * Refactor: Adds latest RxJs version so cancellations work * Refactor: Cleans up the takeUntil code * Refactor: Adds tests for request function * Refactor: Separates into smaller functions * Refactor: Adds last error tests * Started to changed so we require getBackendSrv from the @grafana-runtime when applicable. * Using the getBackendSrv from @grafana/runtime. * Changed so we use the getBackendSrv from the @grafana-runtime when possible. * Fixed so Server Admin -> Orgs works again. * Removed unused dependency. * Fixed digest issues on the Server Admin -> Users page. * Fix: Fixes digest problems in Playlists * Fix: Fixes digest issues in VersionHistory * Tests: Fixes broken tests * Fix: Fixes digest issues in Alerting => Notification channels * Fixed digest issues on the Intive page. * Fixed so we run digest after password reset email sent. * Fixed digest issue when trying to sign up account. * Fixed so the Server Admin -> Edit Org works with backendSrv * Fixed so Server Admin -> Users works with backend srv. * Fixed digest issues in Server Admin -> Orgs * Fix: Fixes digest issues in DashList plugin * Fixed digest issues on Server Admin -> users. * Fix: Fixes digest issues with Snapshots * Fixed digest issue when deleting a user. * Fix: Fixes digest issues with dashLink * Chore: Changes RxJs version to 6.5.4 which includes the same cancellation fix * Fix: Fixes digest issue when toggling folder in manage dashboards * Fix: Fixes bug in executeInOrder * Fix: Fixes digest issue with CreateFolderCtrl and FolderDashboardsCtrl * Fix: Fixes tslint error in test * Refactor: Changes default behaviour for emitted messages as before migration * Fix: Fixes various digest issues when saving, starring or deleting dashboards * Fix: Fixes digest issues with FolderPickerCtrl * Fixed digest issue. * Fixed digest issues. * Fixed issues with angular digest. * Removed the this.digest pattern. Co-authored-by: Hugo Häggmark <hugo.haggmark@gmail.com> Co-authored-by: Marcus Andersson <systemvetaren@gmail.com>
2020-01-21 03:08:07 -06:00
import { backendSrv } from 'app/core/services/backend_srv';
import { promiseToDigest } from 'app/core/utils/promiseToDigest';
export class DashboardImportCtrl {
navModel: any;
step: number;
jsonText: string;
parseError: string;
nameExists: boolean;
uidExists: boolean;
dash: any;
inputs: any[];
inputsValid: boolean;
gnetUrl: string;
gnetError: string;
gnetInfo: any;
titleTouched: boolean;
hasNameValidationError: boolean;
nameValidationError: any;
hasUidValidationError: boolean;
uidValidationError: any;
autoGenerateUid: boolean;
autoGenerateUidValue: string;
2018-06-04 13:29:14 -05:00
folderId: number;
initialFolderTitle: string;
2018-06-04 13:29:14 -05:00
isValidFolderSelection: boolean;
/** @ngInject */
constructor(
private $scope: IScope,
private validationSrv: ValidationSrv,
navModelSrv: NavModelSrv,
private $location: ILocationService,
$routeParams: any
) {
this.navModel = navModelSrv.getNav('create', 'import');
this.step = 1;
this.nameExists = false;
this.uidExists = false;
this.autoGenerateUid = true;
this.autoGenerateUidValue = 'auto-generated';
this.folderId = $routeParams.folderId ? Number($routeParams.folderId) || 0 : null;
this.initialFolderTitle = 'Select a folder';
// check gnetId in url
if ($routeParams.gnetId) {
this.gnetUrl = $routeParams.gnetId;
this.checkGnetDashboard();
}
}
onUpload(dash: any) {
this.dash = dash;
this.dash.id = null;
this.step = 2;
this.inputs = [];
if (this.dash.__inputs) {
for (const input of this.dash.__inputs) {
const inputModel: any = {
name: input.name,
label: input.label,
info: input.description,
value: input.value,
type: input.type,
pluginId: input.pluginId,
2017-12-20 05:33:33 -06:00
options: [],
};
2017-12-20 05:33:33 -06:00
if (input.type === 'datasource') {
this.setDatasourceOptions(input, inputModel);
} else if (!inputModel.info) {
2017-12-20 05:33:33 -06:00
inputModel.info = 'Specify a string constant';
}
this.inputs.push(inputModel);
}
}
this.inputsValid = this.inputs.length === 0;
this.titleChanged();
this.uidChanged(true);
}
setDatasourceOptions(input: { pluginId: string; pluginName: string }, inputModel: any) {
2018-08-26 13:19:23 -05:00
const sources = _.filter(config.datasources, val => {
return val.type === input.pluginId;
});
if (sources.length === 0) {
inputModel.info = 'No data sources of type ' + input.pluginName + ' found';
} else if (!inputModel.info) {
2017-12-20 05:33:33 -06:00
inputModel.info = 'Select a ' + input.pluginName + ' data source';
}
inputModel.options = sources.map(val => {
return { text: val.name, value: val.name };
});
}
inputValueChanged() {
this.inputsValid = true;
for (const input of this.inputs) {
if (!input.value) {
this.inputsValid = false;
}
}
}
titleChanged() {
this.titleTouched = true;
this.nameExists = false;
promiseToDigest(this.$scope)(
this.validationSrv
.validateNewDashboardName(this.folderId, this.dash.title)
.then(() => {
this.nameExists = false;
this.hasNameValidationError = false;
})
.catch(err => {
if (err.type === 'EXISTING') {
this.nameExists = true;
}
this.hasNameValidationError = true;
this.nameValidationError = err.message;
})
);
}
uidChanged(initial: boolean) {
this.uidExists = false;
this.hasUidValidationError = false;
if (initial === true && this.dash.uid) {
this.autoGenerateUidValue = 'value set';
}
if (!this.dash.uid) {
return;
}
promiseToDigest(this.$scope)(
backendSrv
// @ts-ignore
.getDashboardByUid(this.dash.uid)
.then((res: any) => {
this.uidExists = true;
this.hasUidValidationError = true;
this.uidValidationError = `Dashboard named '${res.dashboard.title}' in folder '${res.meta.folderTitle}' has the same uid`;
})
.catch((err: any) => {
err.isHandled = true;
})
);
}
onFolderChange = (folder: any) => {
2018-06-04 13:29:14 -05:00
this.folderId = folder.id;
this.titleChanged();
};
2018-06-04 13:29:14 -05:00
onEnterFolderCreation = () => {
2018-06-04 13:29:14 -05:00
this.inputsValid = false;
};
2018-06-04 13:29:14 -05:00
onExitFolderCreation = () => {
this.inputValueChanged();
};
2018-06-04 13:29:14 -05:00
isValid() {
return this.inputsValid && this.folderId !== null;
}
saveDashboard() {
2018-08-26 13:19:23 -05:00
const inputs = this.inputs.map(input => {
return {
name: input.name,
type: input.type,
pluginId: input.pluginId,
2017-12-20 05:33:33 -06:00
value: input.value,
};
});
return promiseToDigest(this.$scope)(
backendSrv
.post('api/dashboards/import', {
dashboard: this.dash,
overwrite: true,
inputs: inputs,
folderId: this.folderId,
})
.then(res => {
const dashUrl = locationUtil.stripBaseFromUrl(res.importedUrl);
this.$location.url(dashUrl);
})
);
}
loadJsonText() {
try {
2017-12-20 05:33:33 -06:00
this.parseError = '';
2018-08-26 13:19:23 -05:00
const dash = JSON.parse(this.jsonText);
this.onUpload(dash);
} catch (err) {
console.log(err);
this.parseError = err.message;
return;
}
}
checkGnetDashboard() {
2017-12-20 05:33:33 -06:00
this.gnetError = '';
2018-08-26 13:19:23 -05:00
const match = /(^\d+$)|dashboards\/(\d+)/.exec(this.gnetUrl);
let dashboardId;
if (match && match[1]) {
dashboardId = match[1];
} else if (match && match[2]) {
dashboardId = match[2];
} else {
2017-12-20 05:33:33 -06:00
this.gnetError = 'Could not find dashboard';
}
return promiseToDigest(this.$scope)(
backendSrv
.get('api/gnet/dashboards/' + dashboardId)
.then(res => {
this.gnetInfo = res;
// store reference to grafana.com
res.json.gnetId = res.id;
this.onUpload(res.json);
})
.catch(err => {
err.isHandled = true;
this.gnetError = err.data.message || err;
})
);
}
back() {
2017-12-20 05:33:33 -06:00
this.gnetUrl = '';
this.step = 1;
2017-12-20 05:33:33 -06:00
this.gnetError = '';
this.gnetInfo = '';
}
}
export default DashboardImportCtrl;