@craftercms/studio-ui
Version:
Services, components, models & utils to build CrafterCMS authoring extensions.
272 lines (270 loc) • 10.8 kB
JavaScript
/*
* Copyright (C) 2007-2022 Crafter Software Corporation. All Rights Reserved.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License version 3 as published by
* the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
* Copyright (C) 2007-2022 Crafter Software Corporation. All Rights Reserved.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 3 as published by
* the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import TableContainer from '@mui/material/TableContainer';
import Table from '@mui/material/Table';
import TableBody from '@mui/material/TableBody';
import GlobalAppGridRow from '../../GlobalAppGridRow';
import GlobalAppGridCell from '../../GlobalAppGridCell';
import Typography from '@mui/material/Typography';
import React from 'react';
import { FormattedMessage, useIntl } from 'react-intl';
import { makeStyles } from 'tss-react/mui';
import Button from '@mui/material/Button';
import ConfirmDropdown from '../../ConfirmDropdown';
import GlobalAppToolbar from '../../GlobalAppToolbar';
import { messages } from './translations';
import Alert from '@mui/material/Alert';
import translations from '../translations';
import Box from '@mui/material/Box';
import Grid from '@mui/material/Grid';
import { DropDownMenu } from '../../DropDownMenuButton';
const useStyles = makeStyles()((theme) => ({
sectionLabel: {
fontWeight: 400,
color: theme.palette.success.dark
},
conflictedFilesLabel: {
color: theme.palette.error.dark
},
fileName: {
fontWeight: 600
},
revertAllButton: {
color: theme.palette.error.dark,
borderColor: theme.palette.error.main,
marginRight: theme.spacing(2)
},
commitButton: {
color: theme.palette.success.dark,
borderColor: theme.palette.success.main
},
statusNote: {
color: theme.palette.text.secondary
},
conflictActions: {
textAlign: 'right'
},
conflictActionButton: {
marginRight: theme.spacing(2),
color: theme.palette.warning.dark,
borderColor: theme.palette.warning.main
}
}));
export function RepoStatusUI(props) {
const { status, onCommitClick, onResolveConflict, onDiffClick, onBulkAction } = props;
const { classes, cx } = useStyles();
const { formatMessage } = useIntl();
const hasConflicts = status.conflicting.length > 0;
const hasConflictsOrUncommitted = hasConflicts || status.uncommittedChanges.length > 0;
return hasConflictsOrUncommitted
? React.createElement(
React.Fragment,
null,
React.createElement(GlobalAppToolbar, {
title: '',
subtitle: React.createElement(FormattedMessage, {
id: 'repository.statusNote',
defaultMessage:
'Do not use Studio as a git merge and conflict resolution platform. All merge conflicts should be resolved upstream before getting pulled into Studio.'
}),
rightContent: React.createElement(
React.Fragment,
null,
React.createElement(
DropDownMenu,
{
onMenuItemClick: onBulkAction,
variant: 'outlined',
options: [
{
id: 'acceptAll',
primaryText: React.createElement(FormattedMessage, { defaultMessage: 'Accept all Remote' }),
disabled: !hasConflicts
},
{
id: 'keepAll',
primaryText: React.createElement(FormattedMessage, { defaultMessage: 'Keep all Local' }),
disabled: !hasConflicts
},
{
id: 'revertAll',
primaryText: React.createElement(FormattedMessage, { defaultMessage: 'Revert all' })
}
],
menuProps: { sx: { minWidth: 180 } },
sx: { mr: 2 }
},
React.createElement(FormattedMessage, { defaultMessage: 'Bulk actions' })
),
React.createElement(
Button,
{ variant: 'outlined', className: classes.commitButton, onClick: onCommitClick, disabled: hasConflicts },
React.createElement(FormattedMessage, {
id: 'repositories.commitResolution',
defaultMessage: 'Commit Resolution'
})
)
),
showHamburgerMenuButton: false,
showAppsButton: false,
styles: {
toolbar: {
'& > section': {
alignItems: 'start'
}
},
subtitle: {
whiteSpace: 'normal'
}
}
}),
React.createElement(
Box,
{ padding: 2 },
React.createElement(
Grid,
{ container: true, spacing: 2 },
status.conflicting.length > 0 &&
React.createElement(
Grid,
{ item: true, md: 12 },
React.createElement(
Typography,
{ variant: 'h6', className: cx(classes.sectionLabel, classes.conflictedFilesLabel) },
React.createElement(FormattedMessage, {
id: 'repository.conflictedFiles',
defaultMessage: 'Conflicted Files'
})
),
React.createElement(
TableContainer,
null,
React.createElement(
Table,
null,
React.createElement(
TableBody,
null,
status.conflicting.map((file) =>
React.createElement(
GlobalAppGridRow,
{ key: file, className: 'hoverDisabled' },
React.createElement(
GlobalAppGridCell,
{ className: 'width50' },
React.createElement(
'span',
{ className: classes.fileName },
file.substr(file.lastIndexOf('/') + 1)
),
' - ',
file
),
React.createElement(
GlobalAppGridCell,
{ className: classes.conflictActions },
React.createElement(ConfirmDropdown, {
classes: { button: classes.conflictActionButton },
text: formatMessage(messages.acceptRemote),
cancelText: formatMessage(messages.no),
confirmText: formatMessage(messages.yes),
confirmHelperText: formatMessage(messages.acceptRemoteHelper),
onConfirm: () => onResolveConflict('theirs', file)
}),
React.createElement(ConfirmDropdown, {
classes: { button: classes.conflictActionButton },
text: formatMessage(messages.keepLocal),
cancelText: formatMessage(messages.no),
confirmText: formatMessage(messages.yes),
confirmHelperText: formatMessage(messages.keepLocalHelper),
onConfirm: () => onResolveConflict('ours', file)
}),
React.createElement(
Button,
{ variant: 'outlined', onClick: () => onDiffClick(file) },
formatMessage(messages.diff)
)
)
)
)
)
)
),
React.createElement(Box, { sx: { mb: 2 } })
),
status.uncommittedChanges.length > 0 &&
React.createElement(
Grid,
{ item: true, md: 12 },
React.createElement(
Typography,
{ variant: 'h6', className: classes.sectionLabel },
React.createElement(FormattedMessage, {
id: 'repository.pendingCommit',
defaultMessage: 'Pending Commit'
})
),
React.createElement(
TableContainer,
null,
React.createElement(
Table,
null,
React.createElement(
TableBody,
null,
status.uncommittedChanges.map((file) =>
React.createElement(
GlobalAppGridRow,
{ key: file, className: 'hoverDisabled' },
React.createElement(
GlobalAppGridCell,
null,
React.createElement(
'span',
{ className: classes.fileName },
file.substr(file.lastIndexOf('/') + 1)
),
' - ',
file
)
)
)
)
)
)
)
)
)
)
: React.createElement(Alert, { severity: 'success', sx: { m: 2 } }, formatMessage(translations.noConflicts));
}
export default RepoStatusUI;