}
};
Workbench: {
+ DisableSharingURLsUI: boolean;
ArvadosDocsite: string;
FileViewersConfigURL: string;
WelcomePageHTML: string;
WebShell: { ExternalURL: "" },
},
Workbench: {
+ DisableSharingURLsUI: false,
ArvadosDocsite: "",
FileViewersConfigURL: "",
WelcomePageHTML: "",
const loadSharingDialog = async (dispatch: Dispatch, getState: () => RootState, { apiClientAuthorizationService }: ServiceRepository) => {
const dialog = getDialog<SharingDialogData>(getState().dialog, SHARING_DIALOG_NAME);
+ const sharingURLsDisabled = getState().auth.config.clusterConfig.Workbench.DisableSharingURLsUI;
if (dialog) {
dispatch(progressIndicatorActions.START_WORKING(SHARING_DIALOG_NAME));
try {
const resourceUuid = dialog.data.resourceUuid;
await dispatch<any>(initializeManagementForm);
// For collections, we need to load the public sharing tokens
- if (extractUuidObjectType(resourceUuid) === ResourceObjectType.COLLECTION) {
+ if (!sharingURLsDisabled && extractUuidObjectType(resourceUuid) === ResourceObjectType.COLLECTION) {
const sharingTokens = await apiClientAuthorizationService.listCollectionSharingTokens(resourceUuid);
dispatch(resourcesActions.SET_RESOURCES([...sharingTokens.items]));
}
--- /dev/null
+// Copyright (C) The Arvados Authors. All rights reserved.
+//
+// SPDX-License-Identifier: AGPL-3.0
+
+import React from 'react';
+import { mount, configure } from 'enzyme';
+import Adapter from 'enzyme-adapter-react-16';
+import { Provider } from 'react-redux';
+import { combineReducers, createStore } from 'redux';
+
+import SharingDialogComponent, {
+ SharingDialogComponentProps,
+} from './sharing-dialog-component';
+import {
+ extractUuidObjectType,
+ ResourceObjectType
+} from 'models/resource';
+
+configure({ adapter: new Adapter() });
+
+describe("<SharingDialogComponent />", () => {
+ let props: SharingDialogComponentProps;
+ let store;
+
+ beforeEach(() => {
+ const initialAuthState = {
+ config: {
+ keepWebServiceUrl: 'http://example.com/',
+ keepWebInlineServiceUrl: 'http://*.collections.example.com/',
+ }
+ }
+ store = createStore(combineReducers({
+ auth: (state: any = initialAuthState, action: any) => state,
+ }));
+
+ props = {
+ open: true,
+ loading: false,
+ saveEnabled: false,
+ sharedResourceUuid: 'zzzzz-4zz18-zzzzzzzzzzzzzzz',
+ privateAccess: true,
+ sharingURLsNr: 2,
+ sharingURLsDisabled: false,
+ onClose: jest.fn(),
+ onSave: jest.fn(),
+ onCreateSharingToken: jest.fn(),
+ refreshPermissions: jest.fn(),
+ };
+ });
+
+ it("show sharing urls tab on collections when not disabled", () => {
+ expect(props.sharingURLsDisabled).toBe(false);
+ expect(props.sharingURLsNr).toBe(2);
+ expect(extractUuidObjectType(props.sharedResourceUuid) === ResourceObjectType.COLLECTION).toBe(true);
+ let wrapper = mount(<Provider store={store}><SharingDialogComponent {...props} /></Provider>);
+ expect(wrapper.html()).toContain('Sharing URLs (2)');
+
+ // disable Sharing URLs UI
+ props.sharingURLsDisabled = true;
+ wrapper = mount(<Provider store={store}><SharingDialogComponent {...props} /></Provider>);
+ expect(wrapper.html()).not.toContain('Sharing URLs');
+ });
+
+ it("does not show sharing urls on non-collection resources", () => {
+ props.sharedResourceUuid = 'zzzzz-j7d0g-0123456789abcde';
+ expect(extractUuidObjectType(props.sharedResourceUuid) === ResourceObjectType.COLLECTION).toBe(false);
+ expect(props.sharingURLsDisabled).toBe(false);
+ let wrapper = mount(<Provider store={store}><SharingDialogComponent {...props} /></Provider>);
+ expect(wrapper.html()).not.toContain('Sharing URLs');
+ });
+});
\ No newline at end of file
sharedResourceUuid: string;
sharingURLsNr: number;
privateAccess: boolean;
+ sharingURLsDisabled: boolean;
}
export interface SharingDialogActionProps {
onClose: () => void;
PERMISSIONS = 0,
URLS = 1,
}
-export default (props: SharingDialogDataProps & SharingDialogActionProps) => {
+export type SharingDialogComponentProps = SharingDialogDataProps & SharingDialogActionProps;
+
+export default (props: SharingDialogComponentProps) => {
const { open, loading, saveEnabled, sharedResourceUuid,
- sharingURLsNr, privateAccess,
+ sharingURLsNr, privateAccess, sharingURLsDisabled,
onClose, onSave, onCreateSharingToken, refreshPermissions } = props;
- const showTabs = extractUuidObjectType(sharedResourceUuid) === ResourceObjectType.COLLECTION;
+ const showTabs = !sharingURLsDisabled && extractUuidObjectType(sharedResourceUuid) === ResourceObjectType.COLLECTION;
const [tabNr, setTabNr] = React.useState<number>(SharingDialogTab.PERMISSIONS);
const [expDate, setExpDate] = React.useState<Date>();
const [withExpiration, setWithExpiration] = React.useState<boolean>(false);
</Grid>
</>
}
- { tabNr === SharingDialogTab.PERMISSIONS && privateAccess && sharingURLsNr > 0 &&
+ { tabNr === SharingDialogTab.PERMISSIONS && !sharingURLsDisabled &&
+ privateAccess && sharingURLsNr > 0 &&
<Grid item md={12}>
<Typography variant='caption' align='center' color='error'>
Although there aren't specific permissions set, this is publicly accessible via Sharing URL(s).
const mapStateToProps = (state: RootState, { working, ...props }: Props): SharingDialogDataProps => {
const dialog = getDialog<SharingDialogData>(state.dialog, SHARING_DIALOG_NAME);
const sharedResourceUuid = dialog?.data.resourceUuid || '';
+ const sharingURLsDisabled = state.auth.config.clusterConfig.Workbench.DisableSharingURLsUI;
return ({
...props,
saveEnabled: hasChanges(state),
loading: working,
sharedResourceUuid,
- sharingURLsNr: (filterResources(
- (resource: ApiClientAuthorization) =>
+ sharingURLsDisabled,
+ sharingURLsNr: !sharingURLsDisabled
+ ? (filterResources( (resource: ApiClientAuthorization) =>
resource.kind === ResourceKind.API_CLIENT_AUTHORIZATION &&
resource.scopes.includes(`GET /arvados/v1/collections/${sharedResourceUuid}`) &&
resource.scopes.includes(`GET /arvados/v1/collections/${sharedResourceUuid}/`) &&
resource.scopes.includes('GET /arvados/v1/keep_services/accessible')
- )(state.resources) as ApiClientAuthorization[]).length,
+ )(state.resources) as ApiClientAuthorization[]).length
+ : 0,
privateAccess: getSharingPublicAccessFormData(state)?.visibility === VisibilityLevel.PRIVATE,
})
};