handle permissions

This commit is contained in:
Jan Prochazka
2024-08-27 16:32:53 +02:00
parent 74adf1dd3f
commit 94dc292dc9
11 changed files with 101 additions and 56 deletions

View File

@@ -17,6 +17,7 @@
import InputTextModal from '../modals/InputTextModal.svelte'; import InputTextModal from '../modals/InputTextModal.svelte';
import ErrorMessageModal from '../modals/ErrorMessageModal.svelte'; import ErrorMessageModal from '../modals/ErrorMessageModal.svelte';
import { apiCall } from '../utility/api'; import { apiCall } from '../utility/api';
import hasPermission from '../utility/hasPermission';
export let data; export let data;
@@ -140,6 +141,7 @@ await dbgateApi.deployDb(${JSON.stringify(
], ],
data.name != 'default' && data.name != 'default' &&
hasPermission('dbops/model/compare') &&
_.get($currentDatabase, 'connection._id') && { _.get($currentDatabase, 'connection._id') && {
onClick: handleCompareWithCurrentDb, onClick: handleCompareWithCurrentDb,
text: `Compare with ${_.get($currentDatabase, 'name')}`, text: `Compare with ${_.get($currentDatabase, 'name')}`,

View File

@@ -106,6 +106,7 @@
import AboutModal from '../modals/AboutModal.svelte'; import AboutModal from '../modals/AboutModal.svelte';
import { tick } from 'svelte'; import { tick } from 'svelte';
import { getConnectionLabel } from 'dbgate-tools'; import { getConnectionLabel } from 'dbgate-tools';
import hasPermission from '../utility/hasPermission';
export let data; export let data;
export let passProps; export let passProps;
@@ -220,26 +221,27 @@
}; };
return [ return [
config.runAsPortal == false && [ config.runAsPortal == false &&
{ !config.storageDatabase && [
text: $openedConnections.includes(data._id) ? 'View details' : 'Edit', {
onClick: handleOpenConnectionTab, text: $openedConnections.includes(data._id) ? 'View details' : 'Edit',
}, onClick: handleOpenConnectionTab,
!$openedConnections.includes(data._id) && { },
text: 'Delete', !$openedConnections.includes(data._id) && {
onClick: handleDelete, text: 'Delete',
}, onClick: handleDelete,
{ },
text: 'Duplicate', {
onClick: handleDuplicate, text: 'Duplicate',
}, onClick: handleDuplicate,
], },
],
!data.singleDatabase && [ !data.singleDatabase && [
!$openedConnections.includes(data._id) && { !$openedConnections.includes(data._id) && {
text: 'Connect', text: 'Connect',
onClick: handleConnect, onClick: handleConnect,
}, },
{ onClick: handleNewQuery, text: 'New query', isNewQuery: true }, hasPermission(`dbops/query`) && { onClick: handleNewQuery, text: 'New query', isNewQuery: true },
$openedConnections.includes(data._id) && $openedConnections.includes(data._id) &&
data.status && { data.status && {
text: 'Refresh', text: 'Refresh',
@@ -249,7 +251,8 @@
text: 'Disconnect', text: 'Disconnect',
onClick: handleDisconnect, onClick: handleDisconnect,
}, },
$openedConnections.includes(data._id) && hasPermission(`dbops/createdb`) &&
$openedConnections.includes(data._id) &&
driver?.supportedCreateDatabase && driver?.supportedCreateDatabase &&
!data.isReadOnly && { !data.isReadOnly && {
text: 'Create database', text: 'Create database',

View File

@@ -280,20 +280,27 @@
driver?.databaseEngineTypes?.includes('sql') || driver?.databaseEngineTypes?.includes('document'); driver?.databaseEngineTypes?.includes('sql') || driver?.databaseEngineTypes?.includes('document');
return [ return [
{ onClick: handleNewQuery, text: 'New query', isNewQuery: true }, hasPermission(`dbops/query`) && { onClick: handleNewQuery, text: 'New query', isNewQuery: true },
driver?.databaseEngineTypes?.includes('sql') && { onClick: handleNewTable, text: 'New table' }, hasPermission(`dbops/model/edit`) &&
driver?.databaseEngineTypes?.includes('document') && { !connection.isReadOnly &&
onClick: handleNewCollection, driver?.databaseEngineTypes?.includes('sql') && { onClick: handleNewTable, text: 'New table' },
text: `New ${driver?.collectionSingularLabel ?? 'collection/container'}`, !connection.isReadOnly &&
}, hasPermission(`dbops/model/edit`) &&
driver?.databaseEngineTypes?.includes('sql') && { onClick: handleQueryDesigner, text: 'Design query' }, driver?.databaseEngineTypes?.includes('document') && {
onClick: handleNewCollection,
text: `New ${driver?.collectionSingularLabel ?? 'collection/container'}`,
},
hasPermission(`dbops/query`) &&
driver?.databaseEngineTypes?.includes('sql') && { onClick: handleQueryDesigner, text: 'Design query' },
driver?.databaseEngineTypes?.includes('sql') && { driver?.databaseEngineTypes?.includes('sql') && {
onClick: handleNewPerspective, onClick: handleNewPerspective,
text: 'Design perspective query', text: 'Design perspective query',
}, },
{ divider: true }, { divider: true },
isSqlOrDoc && !connection.isReadOnly && { onClick: handleImport, text: 'Import wizard' }, isSqlOrDoc &&
isSqlOrDoc && { onClick: handleExport, text: 'Export wizard' }, !connection.isReadOnly &&
hasPermission(`dbops/import`) && { onClick: handleImport, text: 'Import wizard' },
isSqlOrDoc && hasPermission(`dbops/export`) && { onClick: handleExport, text: 'Export wizard' },
driver?.databaseEngineTypes?.includes('sql') && driver?.databaseEngineTypes?.includes('sql') &&
hasPermission(`dbops/sql-dump/import`) && hasPermission(`dbops/sql-dump/import`) &&
!connection.isReadOnly && { onClick: handleSqlRestore, text: 'Restore/import SQL dump' }, !connection.isReadOnly && { onClick: handleSqlRestore, text: 'Restore/import SQL dump' },
@@ -301,7 +308,9 @@
hasPermission(`dbops/sql-dump/export`) && { onClick: handleSqlDump, text: 'Backup/export SQL dump' }, hasPermission(`dbops/sql-dump/export`) && { onClick: handleSqlDump, text: 'Backup/export SQL dump' },
isSqlOrDoc && isSqlOrDoc &&
!connection.isReadOnly && !connection.isReadOnly &&
!connection.singleDatabase && { onClick: handleDropDatabase, text: 'Drop database' }, !connection.singleDatabase &&
isSqlOrDoc &&
hasPermission(`dbops/dropdb`) && { onClick: handleDropDatabase, text: 'Drop database' },
{ divider: true }, { divider: true },
driver?.databaseEngineTypes?.includes('sql') && { onClick: handleCopyName, text: 'Copy database name' }, driver?.databaseEngineTypes?.includes('sql') && { onClick: handleCopyName, text: 'Copy database name' },
driver?.databaseEngineTypes?.includes('sql') && { onClick: handleShowDiagram, text: 'Show diagram' }, driver?.databaseEngineTypes?.includes('sql') && { onClick: handleShowDiagram, text: 'Show diagram' },
@@ -309,10 +318,14 @@
hasPermission(`dbops/sql-generator`) && { onClick: handleSqlGenerator, text: 'SQL Generator' }, hasPermission(`dbops/sql-generator`) && { onClick: handleSqlGenerator, text: 'SQL Generator' },
driver?.supportsDatabaseProfiler && driver?.supportsDatabaseProfiler &&
hasPermission(`dbops/profiler`) && { onClick: handleDatabaseProfiler, text: 'Database profiler' }, hasPermission(`dbops/profiler`) && { onClick: handleDatabaseProfiler, text: 'Database profiler' },
isSqlOrDoc && { onClick: handleOpenJsonModel, text: 'Open model as JSON' }, isSqlOrDoc &&
isSqlOrDoc && { onClick: handleExportModel, text: 'Export DB model - experimental' }, isSqlOrDoc &&
hasPermission(`dbops/model/view`) && { onClick: handleOpenJsonModel, text: 'Open model as JSON' },
isSqlOrDoc &&
hasPermission(`dbops/model/view`) && { onClick: handleExportModel, text: 'Export DB model - experimental' },
isSqlOrDoc && isSqlOrDoc &&
_.get($currentDatabase, 'connection._id') && _.get($currentDatabase, 'connection._id') &&
hasPermission('dbops/model/compare') &&
(_.get($currentDatabase, 'connection._id') != _.get(connection, '_id') || (_.get($currentDatabase, 'connection._id') != _.get(connection, '_id') ||
(_.get($currentDatabase, 'connection._id') == _.get(connection, '_id') && (_.get($currentDatabase, 'connection._id') == _.get(connection, '_id') &&
_.get($currentDatabase, 'name') != _.get(connection, 'name'))) && { _.get($currentDatabase, 'name') != _.get(connection, 'name'))) && {

View File

@@ -98,12 +98,12 @@
isDrop: true, isDrop: true,
requiresWriteAccess: true, requiresWriteAccess: true,
}, },
{ hasPermission('dbops/table/rename') && {
label: 'Rename table', label: 'Rename table',
isRename: true, isRename: true,
requiresWriteAccess: true, requiresWriteAccess: true,
}, },
{ hasPermission('dbops/table/truncate') && {
label: 'Truncate table', label: 'Truncate table',
isTruncate: true, isTruncate: true,
requiresWriteAccess: true, requiresWriteAccess: true,
@@ -113,29 +113,29 @@
isCopyTableName: true, isCopyTableName: true,
requiresWriteAccess: false, requiresWriteAccess: false,
}, },
{ hasPermission('dbops/table/backup') && {
label: 'Create table backup', label: 'Create table backup',
isDuplicateTable: true, isDuplicateTable: true,
requiresWriteAccess: true, requiresWriteAccess: true,
}, },
{ hasPermission('dbops/model/view') && {
label: 'Show diagram', label: 'Show diagram',
isDiagram: true, isDiagram: true,
}, },
{ {
divider: true, divider: true,
}, },
{ hasPermission('dbops/export') && {
label: 'Export', label: 'Export',
functionName: 'tableReader', functionName: 'tableReader',
isExport: true, isExport: true,
}, },
{ hasPermission('dbops/import') && {
label: 'Import', label: 'Import',
isImport: true, isImport: true,
requiresWriteAccess: true, requiresWriteAccess: true,
}, },
{ hasPermission('dbops/charts') && {
label: 'Open active chart', label: 'Open active chart',
isActiveChart: true, isActiveChart: true,
}, },

View File

@@ -20,6 +20,7 @@
<script lang="ts"> <script lang="ts">
import getElectron from '../utility/getElectron'; import getElectron from '../utility/getElectron';
import hasPermission from '../utility/hasPermission';
import ToolStripCommandButton from './ToolStripCommandButton.svelte'; import ToolStripCommandButton from './ToolStripCommandButton.svelte';
import ToolStripDropDownButton from './ToolStripDropDownButton.svelte'; import ToolStripDropDownButton from './ToolStripDropDownButton.svelte';
@@ -36,8 +37,10 @@
} }
</script> </script>
{#if quickExportHandlerRef} {#if hasPermission('dbops/export')}
<ToolStripDropDownButton menu={getExportMenu} {label} icon="icon export" /> {#if quickExportHandlerRef}
{:else} <ToolStripDropDownButton menu={getExportMenu} {label} icon="icon export" />
<ToolStripCommandButton {command} /> {:else}
<ToolStripCommandButton {command} />
{/if}
{/if} {/if}

View File

@@ -246,10 +246,15 @@
registerQuickExportHandler(quickExportHandler); registerQuickExportHandler(quickExportHandler);
registerMenu({ command: 'collectionDataGrid.openQuery', tag: 'export' }, () => ({ registerMenu({ command: 'collectionDataGrid.openQuery', tag: 'export' }, () =>
...createQuickExportMenu(quickExportHandler, { command: 'collectionDataGrid.export' }), createQuickExportMenu(
tag: 'export', quickExportHandler,
})); {
command: 'collectionDataGrid.export',
},
{ tag: 'export' }
)
);
function handleSetLoadedRows(rows) { function handleSetLoadedRows(rows) {
loadedRows = rows; loadedRows = rows;

View File

@@ -430,6 +430,7 @@
import { openJsonLinesData } from '../utility/openJsonLinesData'; import { openJsonLinesData } from '../utility/openJsonLinesData';
import contextMenuActivator from '../utility/contextMenuActivator'; import contextMenuActivator from '../utility/contextMenuActivator';
import InputTextModal from '../modals/InputTextModal.svelte'; import InputTextModal from '../modals/InputTextModal.svelte';
import hasPermission from '../utility/hasPermission';
export let onLoadNextData = undefined; export let onLoadNextData = undefined;
export let grider = undefined; export let grider = undefined;

View File

@@ -186,10 +186,15 @@
}; };
registerQuickExportHandler(quickExportHandler); registerQuickExportHandler(quickExportHandler);
registerMenu(() => ({ registerMenu(() =>
...createQuickExportMenu(quickExportHandler, { command: 'jslTableGrid.export' }), createQuickExportMenu(
tag: 'export', quickExportHandler,
})); {
command: 'jslTableGrid.export',
},
{ tag: 'export' }
)
);
function handleSetLoadedRows(rows) { function handleSetLoadedRows(rows) {
loadedRows = rows; loadedRows = rows;

View File

@@ -5,7 +5,7 @@
id: 'sqlDataGrid.openActiveChart', id: 'sqlDataGrid.openActiveChart',
category: 'Data grid', category: 'Data grid',
name: 'Open active chart', name: 'Open active chart',
testEnabled: () => getCurrentEditor() != null, testEnabled: () => getCurrentEditor() != null && hasPermission('dbops/charts'),
onClick: () => getCurrentEditor().openActiveChart(), onClick: () => getCurrentEditor().openActiveChart(),
}); });
@@ -13,7 +13,7 @@
id: 'sqlDataGrid.openQuery', id: 'sqlDataGrid.openQuery',
category: 'Data grid', category: 'Data grid',
name: 'Open query', name: 'Open query',
testEnabled: () => getCurrentEditor() != null, testEnabled: () => getCurrentEditor() != null && hasPermission('dbops/query'),
onClick: () => getCurrentEditor().openQuery(), onClick: () => getCurrentEditor().openQuery(),
}); });
@@ -23,7 +23,7 @@
name: 'Export', name: 'Export',
icon: 'icon export', icon: 'icon export',
keyText: 'CtrlOrCommand+E', keyText: 'CtrlOrCommand+E',
testEnabled: () => getCurrentEditor() != null, testEnabled: () => getCurrentEditor() != null && hasPermission('dbops/export'),
onClick: () => getCurrentEditor().exportGrid(), onClick: () => getCurrentEditor().exportGrid(),
}); });
@@ -83,6 +83,7 @@
import ChangeSetGrider from './ChangeSetGrider'; import ChangeSetGrider from './ChangeSetGrider';
import LoadingDataGridCore from './LoadingDataGridCore.svelte'; import LoadingDataGridCore from './LoadingDataGridCore.svelte';
import hasPermission from '../utility/hasPermission';
export let conid; export let conid;
export let display; export let display;
@@ -209,10 +210,14 @@
registerMenu( registerMenu(
{ command: 'sqlDataGrid.openActiveChart', tag: 'chart' }, { command: 'sqlDataGrid.openActiveChart', tag: 'chart' },
{ command: 'sqlDataGrid.openQuery', tag: 'export' }, { command: 'sqlDataGrid.openQuery', tag: 'export' },
() => ({ () =>
...createQuickExportMenu(quickExportHandler, { command: 'sqlDataGrid.export' }), createQuickExportMenu(
tag: 'export', quickExportHandler,
}) {
command: 'sqlDataGrid.export',
},
{ tag: 'export' }
)
); );
function handleSetLoadedRows(rows) { function handleSetLoadedRows(rows) {

View File

@@ -61,6 +61,7 @@
import ToolStripContainer from '../buttons/ToolStripContainer.svelte'; import ToolStripContainer from '../buttons/ToolStripContainer.svelte';
import ToolStripCommandButton from '../buttons/ToolStripCommandButton.svelte'; import ToolStripCommandButton from '../buttons/ToolStripCommandButton.svelte';
import ToolStripButton from '../buttons/ToolStripButton.svelte'; import ToolStripButton from '../buttons/ToolStripButton.svelte';
import hasPermission from '../utility/hasPermission';
export let tabid; export let tabid;
export let conid; export let conid;
@@ -171,7 +172,7 @@
tableInfo={showTable} tableInfo={showTable}
dbInfo={$dbInfo} dbInfo={$dbInfo}
{driver} {driver}
setTableInfo={objectTypeField == 'tables' && !$connection?.isReadOnly setTableInfo={objectTypeField == 'tables' && !$connection?.isReadOnly && hasPermission(`dbops/model/edit`)
? tableInfoUpdater => ? tableInfoUpdater =>
setEditorData(tbl => setEditorData(tbl =>
tbl tbl

View File

@@ -1,5 +1,6 @@
import type { QuickExportDefinition } from 'dbgate-types'; import type { QuickExportDefinition } from 'dbgate-types';
import { currentArchive, getCurrentArchive, getExtensions } from '../stores'; import { currentArchive, getCurrentArchive, getExtensions } from '../stores';
import hasPermission from './hasPermission';
export function createQuickExportMenuItems(handler: (fmt: QuickExportDefinition) => Function, advancedExportMenuItem) { export function createQuickExportMenuItems(handler: (fmt: QuickExportDefinition) => Function, advancedExportMenuItem) {
const extensions = getExtensions(); const extensions = getExtensions();
@@ -34,10 +35,16 @@ export function createQuickExportMenuItems(handler: (fmt: QuickExportDefinition)
export default function createQuickExportMenu( export default function createQuickExportMenu(
handler: (fmt: QuickExportDefinition) => Function, handler: (fmt: QuickExportDefinition) => Function,
advancedExportMenuItem advancedExportMenuItem,
additionalFields = {}
) { ) {
if (!hasPermission('dbops/export')) {
return null;
}
return { return {
text: 'Export', text: 'Export',
submenu: createQuickExportMenuItems(handler, advancedExportMenuItem), submenu: createQuickExportMenuItems(handler, advancedExportMenuItem),
...advancedExportMenuItem,
}; };
} }