Skip to content

Commit

Permalink
Merge pull request #7109 from strapi/chore/ml-delete-assets
Browse files Browse the repository at this point in the history
Chore/ml delete assets
  • Loading branch information
alexandrebodin committed Aug 12, 2020
2 parents 99dfd24 + 95e6837 commit c9ece30
Show file tree
Hide file tree
Showing 5 changed files with 119 additions and 87 deletions.
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { useEffect, useState } from 'react';
import PropTypes from 'prop-types';
import { useDebounce } from '@buffetjs/hooks';
import { HeaderSearch, useGlobalContext, useQuery } from 'strapi-helper-plugin';
import { HeaderSearch, useGlobalContext, useQuery, LoadingIndicator } from 'strapi-helper-plugin';
import { useAppContext } from '../../../hooks';
import { getTrad, getFileModelTimestamps } from '../../../utils';

Expand All @@ -15,6 +15,7 @@ const HomePageSettings = ({
areAllCheckboxesSelected,
filters,
hasSomeCheckboxSelected,
isLoading,
onChange,
onFilterDelete,
onSelectAll,
Expand Down Expand Up @@ -54,21 +55,28 @@ const HomePageSettings = ({
value={searchValue}
autoFocus="true"
/>
<ControlsWrapper>
{canUpdate && (
<>
<SelectAll
onChange={onSelectAll}
checked={areAllCheckboxesSelected}
someChecked={hasSomeCheckboxSelected && !areAllCheckboxesSelected}
/>
<Padded right />
</>
)}
<SortPicker onChange={onChange} value={query.get('_sort') || `${updated_at}:DESC`} />
<Padded right />
<Filters onChange={onChange} filters={filters} onClick={onFilterDelete} />
</ControlsWrapper>
{isLoading ? (
<>
<Padded top bottom size="lg" />
<LoadingIndicator />
</>
) : (
<ControlsWrapper>
{canUpdate && (
<>
<SelectAll
onChange={onSelectAll}
checked={areAllCheckboxesSelected}
someChecked={hasSomeCheckboxSelected && !areAllCheckboxesSelected}
/>
<Padded right />
</>
)}
<SortPicker onChange={onChange} value={query.get('_sort') || `${updated_at}:DESC`} />
<Padded right />
<Filters onChange={onChange} filters={filters} onClick={onFilterDelete} />
</ControlsWrapper>
)}
</>
);
};
Expand All @@ -86,6 +94,7 @@ HomePageSettings.propTypes = {
areAllCheckboxesSelected: PropTypes.bool,
filters: PropTypes.array,
hasSomeCheckboxSelected: PropTypes.bool,
isLoading: PropTypes.bool.isRequired,
onChange: PropTypes.func,
onFilterDelete: PropTypes.func,
onSelectAll: PropTypes.func,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ const HomePageContent = ({
data,
dataCount,
dataToDelete,
isLoading,
onCardCheck,
onCardClick,
onClick,
Expand Down Expand Up @@ -41,6 +42,7 @@ const HomePageContent = ({
areAllCheckboxesSelected={areAllCheckboxesSelected}
filters={filters}
hasSomeCheckboxSelected={hasSomeCheckboxSelected}
isLoading={isLoading}
onChange={onParamsChange}
onFilterDelete={onFilterDelete}
onSelectAll={onSelectAll}
Expand All @@ -63,6 +65,7 @@ HomePageContent.defaultProps = {
data: [],
dataCount: 0,
dataToDelete: [],
isLoading: false,
onCardCheck: () => {},
onCardClick: () => {},
onClick: () => {},
Expand All @@ -75,6 +78,7 @@ HomePageContent.propTypes = {
data: PropTypes.array,
dataCount: PropTypes.number,
dataToDelete: PropTypes.array,
isLoading: PropTypes.bool,
onCardCheck: PropTypes.func,
onCardClick: PropTypes.func,
onClick: PropTypes.func,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
import React, { useReducer, useRef, useState, useEffect } from 'react';
import React, { useCallback, useReducer, useRef, useState, useEffect } from 'react';
import { get, includes, toString, isEqual, intersectionWith } from 'lodash';
import { useHistory, useLocation } from 'react-router-dom';
import { Header } from '@buffetjs/custom';
import { Button } from '@buffetjs/core';
import {
PopUpWarning,
LoadingIndicator,
useGlobalContext,
generateFiltersFromSearch,
generateSearchFromFilters,
Expand Down Expand Up @@ -39,7 +38,14 @@ const HomePage = () => {
const { push } = useHistory();
const { search } = useLocation();
const isMounted = useRef(true);
const { data, dataCount, dataToDelete, isLoading } = reducerState.toJS();
const {
data,
dataCount,
dataToDelete,
isLoading,
shouldRefetchData,
showModalConfirmButtonLoading,
} = reducerState.toJS();
const pluginName = formatMessage({ id: getTrad('plugin.name') });
const paramsKeys = ['_limit', '_start', '_q', '_sort'];

Expand Down Expand Up @@ -211,51 +217,34 @@ const HomePage = () => {
push({ search: newSearch });
};

// FIXME: the delete logic should be redone
const handleDeleteMediaFromModal = async id => {
handleClickToggleModal();

lockAppWithOverlay();

try {
await deleteMedia(id);

strapi.notification.success('notification.success.delete');

dispatch({
type: 'ON_DELETE_MEDIA_SUCCEEDED',
mediaId: id,
});
} catch (err) {
strapi.notification.error(err);
} finally {
strapi.unlockApp();
}
};

// FIXME: the delete logic should be redone
const handleDeleteMedias = async () => {
setIsPopupOpen(false);

lockAppWithOverlay();
const handleConfirmDeleteMedias = useCallback(async () => {
dispatch({ type: 'ON_DELETE_MEDIAS' });

try {
await Promise.all(dataToDelete.map(item => deleteMedia(item.id)));

dispatch({
type: 'CLEAR_DATA_TO_DELETE',
type: 'ON_DELETE_MEDIAS_SUCCEEDED',
});
} catch (err) {
strapi.notification.error(err);

dispatch({
type: 'ON_DELETE_MEDIA_ERROR',
type: 'ON_DELETE_MEDIAS_ERROR',
});
} finally {
setIsPopupOpen(false);
}
}, [dataToDelete]);

const handleClosedModalDeleteAll = useCallback(() => {
if (shouldRefetchData) {
fetchListData();
strapi.unlockApp();
} else {
dispatch({ type: 'RESET_DATA_TO_DELETE' });
}
};
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [shouldRefetchData]);

const handleModalClose = () => {
resetModalState();
Expand All @@ -272,15 +261,6 @@ const HomePage = () => {
});
};

const lockAppWithOverlay = () => {
const overlayblockerParams = {
children: <div />,
noGradient: true,
};

strapi.lockApp(overlayblockerParams);
};

const resetModalState = () => {
setModalInitialStep('browse');
setFileToEdit(null);
Expand Down Expand Up @@ -333,11 +313,19 @@ const HomePage = () => {
],
};

const handleRemoveFileFromDataToDelete = useCallback(id => {
dispatch({
type: 'ON_CHANGE_DATA_TO_DELETE',
id,
});
}, []);

const content = canRead ? (
<HomePageContent
data={data}
dataCount={dataCount}
dataToDelete={dataToDelete}
isLoading={isLoading}
onCardCheck={handleChangeCheck}
onCardClick={handleClickEditFile}
onClick={handleClickToggleModal}
Expand All @@ -350,28 +338,23 @@ const HomePage = () => {
return (
<Container>
<Header {...headerProps} isLoading={isLoading} />
{isLoading ? (
<>
<Padded top bottom size="lg" />
<LoadingIndicator />
</>
) : (
content
)}
{content}
<ModalStepper
initialFileToEdit={fileToEdit}
initialStep={modalInitialStep}
isOpen={isModalOpen}
onClosed={handleModalClose}
onDeleteMedia={handleDeleteMediaFromModal}
onRemoveFileFromDataToDelete={handleRemoveFileFromDataToDelete}
onToggle={handleClickToggleModal}
refetchData={fetchListData}
/>
<PopUpWarning
isOpen={isPopupOpen}
isConfirmButtonLoading={showModalConfirmButtonLoading}
onConfirm={handleConfirmDeleteMedias}
onClosed={handleClosedModalDeleteAll}
toggleModal={handleClickTogglePopup}
popUpWarningType="danger"
onConfirm={handleDeleteMedias}
/>
<Padded bottom size="md" />
<Padded bottom size="md" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ const initialState = fromJS({
dataCount: 0,
dataToDelete: [],
isLoading: true,
showModalConfirmButtonLoading: false,
shouldRefetchData: false,
});

const reducer = (state, action) => {
Expand Down Expand Up @@ -40,12 +42,26 @@ const reducer = (state, action) => {

return state.removeIn(['dataToDelete', index]);
}
case 'ON_DELETE_MEDIA_SUCCEEDED':
case 'ON_DELETE_MEDIAS': {
return state.update('showModalConfirmButtonLoading', () => true);
}
case 'ON_DELETE_MEDIAS_SUCCEEDED': {
return state
.update('data', list => list.filter(item => item.get('id') !== action.mediaId))
.update('dataCount', count => count - 1);
case 'ON_DELETE_MEDIA_ERROR':
return state.update('dataToDelete', () => fromJS([]));
.update('dataToDelete', () => fromJS([]))
.update('shouldRefetchData', () => true)
.update('showModalConfirmButtonLoading', () => false);
}
case 'ON_DELETE_MEDIAS_ERROR': {
return state
.update('dataToDelete', () => fromJS([]))
.update('showModalConfirmButtonLoading', () => false);
}
case 'RESET_DATA_TO_DELETE': {
return state
.update('dataToDelete', () => fromJS([]))
.update('shouldRefetchData', () => false)
.update('showModalConfirmButtonLoading', () => false);
}
case 'TOGGLE_SELECT_ALL': {
const isSelected = state.get('data').every(item => state.get('dataToDelete').includes(item));

Expand Down

0 comments on commit c9ece30

Please sign in to comment.