Skip to content

Commit

Permalink
feat(can_share): can share chart and dashboard (#14076)
Browse files Browse the repository at this point in the history
* feat: share chart  - can_share_chart
share dashboard can_share_dashboard

* fix: pre-commit

* fix: userCanShare tests

* fix: after hugh CR

* fix: adjust after spa refactor
  • Loading branch information
amitmiran137 authored Apr 13, 2021
1 parent b394733 commit 9c5264a
Show file tree
Hide file tree
Showing 10 changed files with 64 additions and 28 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ describe('HeaderActionsDropdown', () => {
}

describe('readonly-user', () => {
const overrideProps = { userCanSave: false };
const overrideProps = { userCanSave: false, userCanShare: false };

it('should render the DropdownButton', () => {
const { wrapper } = setup(overrideProps);
Expand All @@ -89,9 +89,9 @@ describe('HeaderActionsDropdown', () => {
expect(menu.find(RefreshIntervalModal)).toExist();
});

it('should render the ShareMenuItems', () => {
it('should not render the ShareMenuItems', () => {
const { menu } = setup(overrideProps);
expect(menu.find(ShareMenuItems)).toExist();
expect(menu.find(ShareMenuItems)).not.toExist();
});

it('should not render the CssEditor', () => {
Expand All @@ -101,7 +101,7 @@ describe('HeaderActionsDropdown', () => {
});

describe('write-user', () => {
const overrideProps = { userCanSave: true };
const overrideProps = { userCanSave: true, userCanShare: true };

it('should render the DropdownButton', () => {
const { wrapper } = setup(overrideProps);
Expand Down Expand Up @@ -135,7 +135,11 @@ describe('HeaderActionsDropdown', () => {
});

describe('write-user-with-edit-mode', () => {
const overrideProps = { userCanSave: true, editMode: true };
const overrideProps = {
userCanSave: true,
editMode: true,
userCanShare: true,
};

it('should render the DropdownButton', () => {
const { wrapper } = setup(overrideProps);
Expand Down
10 changes: 10 additions & 0 deletions superset-frontend/src/dashboard/actions/hydrate.js
Original file line number Diff line number Diff line change
Expand Up @@ -313,7 +313,17 @@ export const hydrateDashboard = (dashboardData, chartData, datasourcesData) => (
userId: String(user.userId), // legacy, please use state.user instead
dash_edit_perm: getPermissions('can_write', 'Dashboard', roles),
dash_save_perm: getPermissions('can_save_dash', 'Superset', roles),
dash_share_perm: getPermissions(
'can_share_dashboard',
'Superset',
roles,
),
superset_can_explore: getPermissions('can_explore', 'Superset', roles),
superset_can_share: getPermissions(
'can_share_chart',
'Superset',
roles,
),
superset_can_csv: getPermissions('can_csv', 'Superset', roles),
slice_can_edit: getPermissions('can_slice', 'Superset', roles),
common: {
Expand Down
2 changes: 2 additions & 0 deletions superset-frontend/src/dashboard/components/Header.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -375,6 +375,7 @@ class Header extends React.PureComponent {
} = this.props;

const userCanEdit = dashboardInfo.dash_edit_perm;
const userCanShare = dashboardInfo.dash_share_perm;
const userCanSaveAs = dashboardInfo.dash_save_perm;
const refreshLimit =
dashboardInfo.common.conf.SUPERSET_DASHBOARD_PERIODICAL_REFRESH_LIMIT;
Expand Down Expand Up @@ -542,6 +543,7 @@ class Header extends React.PureComponent {
editMode={editMode}
hasUnsavedChanges={hasUnsavedChanges}
userCanEdit={userCanEdit}
userCanShare={userCanShare}
userCanSave={userCanSaveAs}
isLoading={isLoading}
showPropertiesModal={this.showPropertiesModal}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ const propTypes = {
startPeriodicRender: PropTypes.func.isRequired,
editMode: PropTypes.bool.isRequired,
userCanEdit: PropTypes.bool.isRequired,
userCanShare: PropTypes.bool.isRequired,
userCanSave: PropTypes.bool.isRequired,
isLoading: PropTypes.bool.isRequired,
layout: PropTypes.object.isRequired,
Expand Down Expand Up @@ -192,6 +193,7 @@ class HeaderActionsDropdown extends React.PureComponent {
expandedSlices,
onSave,
userCanEdit,
userCanShare,
userCanSave,
isLoading,
refreshLimit,
Expand Down Expand Up @@ -241,15 +243,17 @@ class HeaderActionsDropdown extends React.PureComponent {
/>
</Menu.Item>
)}
<ShareMenuItems
url={url}
copyMenuItemTitle={t('Copy dashboard URL')}
emailMenuItemTitle={t('Share dashboard by email')}
emailSubject={emailSubject}
emailBody={emailBody}
addSuccessToast={addSuccessToast}
addDangerToast={addDangerToast}
/>
{userCanShare && (
<ShareMenuItems
url={url}
copyMenuItemTitle={t('Copy dashboard URL')}
emailMenuItemTitle={t('Share dashboard by email')}
emailSubject={emailSubject}
emailBody={emailBody}
addSuccessToast={addSuccessToast}
addDangerToast={addDangerToast}
/>
)}
<Menu.Item
key={MENU_KEYS.REFRESH_DASHBOARD}
data-test="refresh-dashboard-menu-item"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ type SliceHeaderProps = {
annotationError?: object;
sliceName?: string;
supersetCanExplore?: boolean;
supersetCanShare?: boolean;
supersetCanCSV?: boolean;
sliceCanEdit?: boolean;
componentId: string;
Expand Down Expand Up @@ -83,6 +84,7 @@ const SliceHeader: FC<SliceHeaderProps> = ({
isExpanded = [],
sliceName = '',
supersetCanExplore = false,
supersetCanShare = false,
supersetCanCSV = false,
sliceCanEdit = false,
slice,
Expand Down Expand Up @@ -172,6 +174,7 @@ const SliceHeader: FC<SliceHeaderProps> = ({
exploreChart={exploreChart}
exportCSV={exportCSV}
supersetCanExplore={supersetCanExplore}
supersetCanShare={supersetCanShare}
supersetCanCSV={supersetCanCSV}
sliceCanEdit={sliceCanEdit}
componentId={componentId}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ const propTypes = {
isExpanded: PropTypes.bool,
updatedDttm: PropTypes.number,
supersetCanExplore: PropTypes.bool,
supersetCanShare: PropTypes.bool,
supersetCanCSV: PropTypes.bool,
sliceCanEdit: PropTypes.bool,
toggleExpandSlice: PropTypes.func,
Expand All @@ -61,6 +62,7 @@ const defaultProps = {
isCached: [],
isExpanded: false,
supersetCanExplore: false,
supersetCanShare: false,
supersetCanCSV: false,
sliceCanEdit: false,
};
Expand All @@ -72,7 +74,6 @@ const MENU_KEYS = {
EXPLORE_CHART: 'explore_chart',
EXPORT_CSV: 'export_csv',
RESIZE_LABEL: 'resize_label',
SHARE_CHART: 'share_chart',
DOWNLOAD_AS_IMAGE: 'download_as_image',
};

Expand Down Expand Up @@ -188,6 +189,7 @@ class SliceHeaderControls extends React.PureComponent {
addSuccessToast,
addDangerToast,
isFullSize,
supersetCanShare,
} = this.props;
const crossFilterItems = getChartMetadataRegistry().items;
const isCrossFilter = Object.entries(crossFilterItems)
Expand Down Expand Up @@ -253,18 +255,20 @@ class SliceHeaderControls extends React.PureComponent {
</Menu.Item>
)}

<ShareMenuItems
url={getDashboardUrl(
window.location.pathname,
getActiveFilters(),
componentId,
)}
copyMenuItemTitle={t('Copy chart URL')}
emailMenuItemTitle={t('Share chart by email')}
emailSubject={t('Superset chart')}
addSuccessToast={addSuccessToast}
addDangerToast={addDangerToast}
/>
{supersetCanShare && (
<ShareMenuItems
url={getDashboardUrl(
window.location.pathname,
getActiveFilters(),
componentId,
)}
copyMenuItemTitle={t('Copy chart URL')}
emailMenuItemTitle={t('Share chart by email')}
emailSubject={t('Superset chart')}
addSuccessToast={addSuccessToast}
addDangerToast={addDangerToast}
/>
)}

<Menu.Item key={MENU_KEYS.RESIZE_LABEL}>{resizeLabel}</Menu.Item>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ const propTypes = {
isExpanded: PropTypes.bool.isRequired,
isCached: PropTypes.bool,
supersetCanExplore: PropTypes.bool.isRequired,
supersetCanShare: PropTypes.bool.isRequired,
supersetCanCSV: PropTypes.bool.isRequired,
sliceCanEdit: PropTypes.bool.isRequired,
addSuccessToast: PropTypes.func.isRequired,
Expand Down Expand Up @@ -256,6 +257,7 @@ export default class Chart extends React.Component {
toggleExpandSlice,
timeout,
supersetCanExplore,
supersetCanShare,
supersetCanCSV,
sliceCanEdit,
addSuccessToast,
Expand Down Expand Up @@ -311,6 +313,7 @@ export default class Chart extends React.Component {
updateSliceName={updateSliceName}
sliceName={sliceName}
supersetCanExplore={supersetCanExplore}
supersetCanShare={supersetCanShare}
supersetCanCSV={supersetCanCSV}
sliceCanEdit={sliceCanEdit}
componentId={componentId}
Expand Down
1 change: 1 addition & 0 deletions superset-frontend/src/dashboard/containers/Chart.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,7 @@ function mapStateToProps(
editMode: dashboardState.editMode,
isExpanded: !!dashboardState.expandedSlices[id],
supersetCanExplore: !!dashboardInfo.superset_can_explore,
supersetCanShare: !!dashboardInfo.superset_can_share,
supersetCanCSV: !!dashboardInfo.superset_can_csv,
sliceCanEdit: !!dashboardInfo.slice_can_edit,
ownCurrentState: dataMask.ownFilters?.[id]?.currentState,
Expand Down
2 changes: 2 additions & 0 deletions superset/security/manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -556,6 +556,8 @@ def create_custom_permissions(self) -> None:
self.add_permission_view_menu("all_datasource_access", "all_datasource_access")
self.add_permission_view_menu("all_database_access", "all_database_access")
self.add_permission_view_menu("all_query_access", "all_query_access")
self.add_permission_view_menu("can_share_dashboard", "Superset")
self.add_permission_view_menu("can_share_chart", "Superset")

def create_missing_perms(self) -> None:
"""
Expand Down
5 changes: 4 additions & 1 deletion tests/security_tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -670,12 +670,13 @@ def assert_can_gamma(self, perm_set):
self.assertIn(("can_csv", "Superset"), perm_set)
self.assertIn(("can_dashboard", "Superset"), perm_set)
self.assertIn(("can_explore", "Superset"), perm_set)
self.assertIn(("can_share_chart", "Superset"), perm_set)
self.assertIn(("can_share_dashboard", "Superset"), perm_set)
self.assertIn(("can_explore_json", "Superset"), perm_set)
self.assertIn(("can_fave_dashboards", "Superset"), perm_set)
self.assertIn(("can_fave_slices", "Superset"), perm_set)
self.assertIn(("can_save_dash", "Superset"), perm_set)
self.assertIn(("can_slice", "Superset"), perm_set)
self.assertIn(("can_explore", "Superset"), perm_set)
self.assertIn(("can_explore_json", "Superset"), perm_set)
self.assertIn(("can_userinfo", "UserDBModelView"), perm_set)
self.assert_can_menu("Databases", perm_set)
Expand Down Expand Up @@ -868,6 +869,8 @@ def test_gamma_permissions(self):
self.assertIn(("can_csv", "Superset"), gamma_perm_set)
self.assertIn(("can_dashboard", "Superset"), gamma_perm_set)
self.assertIn(("can_explore", "Superset"), gamma_perm_set)
self.assertIn(("can_share_chart", "Superset"), gamma_perm_set)
self.assertIn(("can_share_dashboard", "Superset"), gamma_perm_set)
self.assertIn(("can_explore_json", "Superset"), gamma_perm_set)
self.assertIn(("can_fave_dashboards", "Superset"), gamma_perm_set)
self.assertIn(("can_fave_slices", "Superset"), gamma_perm_set)
Expand Down

0 comments on commit 9c5264a

Please sign in to comment.