mirror of
https://github.com/dbeaver/cloudbeaver.git
synced 2026-10-30 23:04:30 +08:00
* CB-5342 fix: database data source tasks result * CB-5342 fix: database data source tasks tracking * CB-5342 fix: add stop auto refresh button
204 lines
6.7 KiB
TypeScript
204 lines
6.7 KiB
TypeScript
/*
|
|
* CloudBeaver - Cloud Database Manager
|
|
* Copyright (C) 2020-2024 DBeaver Corp and others
|
|
*
|
|
* Licensed under the Apache License, Version 2.0.
|
|
* you may not use this file except in compliance with the License.
|
|
*/
|
|
import { observable } from 'mobx';
|
|
|
|
import { importLazyComponent } from '@cloudbeaver/core-blocks';
|
|
import { IDataContextProvider } from '@cloudbeaver/core-data-context';
|
|
import { Bootstrap, injectable } from '@cloudbeaver/core-di';
|
|
import { CommonDialogService, DialogueStateResult } from '@cloudbeaver/core-dialogs';
|
|
import { LocalizationService } from '@cloudbeaver/core-localization';
|
|
import { declensionOfNumber } from '@cloudbeaver/core-utils';
|
|
import { ACTION_REFRESH, ActionService, MenuBaseItem, menuExtractItems, MenuSeparatorItem, MenuService } from '@cloudbeaver/core-view';
|
|
|
|
import { IDatabaseRefreshState } from '../../../../DatabaseDataModel/Actions/DatabaseRefreshAction';
|
|
import { DATA_CONTEXT_DV_DDM } from '../../../../DatabaseDataModel/DataContext/DATA_CONTEXT_DV_DDM';
|
|
import { DATA_CONTEXT_DV_DDM_RESULT_INDEX } from '../../../../DatabaseDataModel/DataContext/DATA_CONTEXT_DV_DDM_RESULT_INDEX';
|
|
import { DATA_VIEWER_DATA_MODEL_ACTIONS_MENU } from '../DATA_VIEWER_DATA_MODEL_ACTIONS_MENU';
|
|
import { getRefreshState } from './getRefreshState';
|
|
import { MENU_DATA_VIEWER_AUTO_REFRESH } from './MENU_DATA_VIEWER_AUTO_REFRESH';
|
|
|
|
const AutoRefreshSettingsDialog = importLazyComponent(() => import('./AutoRefreshSettingsDialog').then(module => module.AutoRefreshSettingsDialog));
|
|
|
|
const AUTO_REFRESH_INTERVALS = [5, 10, 15, 30, 60];
|
|
|
|
@injectable()
|
|
export class TableRefreshActionBootstrap extends Bootstrap {
|
|
constructor(
|
|
private readonly actionService: ActionService,
|
|
private readonly menuService: MenuService,
|
|
private readonly localizationService: LocalizationService,
|
|
private readonly commonDialogService: CommonDialogService,
|
|
) {
|
|
super();
|
|
}
|
|
|
|
register() {
|
|
this.registerGeneralActions();
|
|
}
|
|
|
|
private registerGeneralActions() {
|
|
this.menuService.addCreator({
|
|
menus: [DATA_VIEWER_DATA_MODEL_ACTIONS_MENU],
|
|
contexts: [DATA_CONTEXT_DV_DDM, DATA_CONTEXT_DV_DDM_RESULT_INDEX],
|
|
isApplicable(context) {
|
|
const model = context.get(DATA_CONTEXT_DV_DDM)!;
|
|
const resultIndex = context.get(DATA_CONTEXT_DV_DDM_RESULT_INDEX)!;
|
|
|
|
return !model.isDisabled(resultIndex);
|
|
},
|
|
getItems(context, items) {
|
|
return [MENU_DATA_VIEWER_AUTO_REFRESH, ...items];
|
|
},
|
|
orderItems(context, items) {
|
|
const extracted = menuExtractItems(items, [MENU_DATA_VIEWER_AUTO_REFRESH]);
|
|
return [...extracted, ...items];
|
|
},
|
|
});
|
|
this.menuService.addCreator({
|
|
menus: [MENU_DATA_VIEWER_AUTO_REFRESH],
|
|
contexts: [DATA_CONTEXT_DV_DDM, DATA_CONTEXT_DV_DDM_RESULT_INDEX],
|
|
isApplicable(context) {
|
|
const model = context.get(DATA_CONTEXT_DV_DDM)!;
|
|
const resultIndex = context.get(DATA_CONTEXT_DV_DDM_RESULT_INDEX)!;
|
|
|
|
return !model.isDisabled(resultIndex);
|
|
},
|
|
getItems: (context, items) => {
|
|
const state = getRefreshState(context);
|
|
items = [...items];
|
|
for (const interval of AUTO_REFRESH_INTERVALS) {
|
|
const label = this.getLabel(interval);
|
|
items.push(
|
|
new MenuBaseItem(
|
|
{
|
|
id: `auto-refresh-${interval}`,
|
|
label,
|
|
tooltip: label,
|
|
disabled: state?.interval === interval * 1000,
|
|
},
|
|
{
|
|
onSelect: () => {
|
|
state?.setInterval(interval * 1000);
|
|
},
|
|
},
|
|
),
|
|
);
|
|
}
|
|
|
|
items.push(new MenuSeparatorItem());
|
|
|
|
items.push(
|
|
new MenuBaseItem(
|
|
{
|
|
id: 'auto-refresh-custom',
|
|
label: 'ui_custom',
|
|
tooltip: 'plugin_data_viewer_action_auto_refresh_custom',
|
|
},
|
|
{
|
|
onSelect: this.configureAutoRefresh.bind(this, context),
|
|
},
|
|
),
|
|
);
|
|
|
|
items.push(
|
|
new MenuBaseItem(
|
|
{
|
|
id: 'auto-refresh-stop',
|
|
label: 'ui_processing_stop',
|
|
tooltip: 'data_viewer_action_auto_refresh_stop',
|
|
disabled: !state?.isAutoRefresh,
|
|
},
|
|
{
|
|
onSelect: () => {
|
|
state?.setInterval(0);
|
|
},
|
|
},
|
|
),
|
|
);
|
|
|
|
return items;
|
|
},
|
|
});
|
|
this.actionService.addHandler({
|
|
id: 'data-base-handler',
|
|
contexts: [DATA_CONTEXT_DV_DDM, DATA_CONTEXT_DV_DDM_RESULT_INDEX],
|
|
menus: [DATA_VIEWER_DATA_MODEL_ACTIONS_MENU, MENU_DATA_VIEWER_AUTO_REFRESH],
|
|
actions: [ACTION_REFRESH],
|
|
isDisabled(context) {
|
|
const model = context.get(DATA_CONTEXT_DV_DDM)!;
|
|
|
|
return model.isLoading();
|
|
},
|
|
getActionInfo(context, action) {
|
|
if (action === ACTION_REFRESH) {
|
|
const state = getRefreshState(context);
|
|
return {
|
|
...action.info,
|
|
icon: state?.isAutoRefresh ? '/icons/timer_m.svg#root' : '/icons/refresh_m.svg#root',
|
|
label: '',
|
|
tooltip: state?.isAutoRefresh ? 'data_viewer_action_auto_refresh_stop' : 'data_viewer_action_refresh',
|
|
};
|
|
}
|
|
|
|
return action.info;
|
|
},
|
|
handler: context => {
|
|
const model = context.get(DATA_CONTEXT_DV_DDM)!;
|
|
const state = getRefreshState(context);
|
|
|
|
if (state?.isAutoRefresh) {
|
|
state.setInterval(0);
|
|
} else {
|
|
model.refresh();
|
|
}
|
|
},
|
|
});
|
|
}
|
|
|
|
private async configureAutoRefresh(context: IDataContextProvider) {
|
|
const state = getRefreshState(context);
|
|
if (!state) {
|
|
return;
|
|
}
|
|
|
|
const stateCopy = observable<IDatabaseRefreshState>({
|
|
interval: state.interval / 1000,
|
|
paused: state.paused,
|
|
stopOnError: state.stopOnError,
|
|
});
|
|
|
|
const result = await this.commonDialogService.open(AutoRefreshSettingsDialog, { state: stateCopy });
|
|
|
|
if (result === DialogueStateResult.Resolved) {
|
|
let interval = stateCopy.interval;
|
|
|
|
if (typeof interval === 'string') {
|
|
interval = Number.parseInt(interval);
|
|
}
|
|
|
|
if (!Number.isInteger(interval)) {
|
|
interval = 0;
|
|
}
|
|
|
|
state.setInterval(interval * 1000);
|
|
state.setStopOnError(stateCopy.stopOnError);
|
|
}
|
|
}
|
|
|
|
private getLabel(interval: number) {
|
|
let message = ['ui_second_first_form', 'ui_second_second_form', 'ui_second_third_form'];
|
|
|
|
if (interval >= 60) {
|
|
message = ['ui_minute_first_form', 'ui_minute_second_form', 'ui_minute_third_form'];
|
|
interval = Math.round(interval / 60);
|
|
}
|
|
|
|
return this.localizationService.translate(declensionOfNumber(interval, message), undefined, { interval });
|
|
}
|
|
}
|