-
Alexandru Munteanu authored2358e7be
Code owners
Assign users and groups as approvers for specific file changes. Learn more.
import React, { Fragment } from 'react'
import { get } from 'lodash'
import { Button } from '@pubsweet/ui'
import { connect } from 'react-redux'
import styled from 'styled-components'
import { th } from '@pubsweet/ui-toolkit'
import { actions } from 'pubsweet-client'
import { ConnectPage } from 'xpub-connect'
import { withJournal } from 'xpub-journal'
import { compose, withHandlers, withProps } from 'recompose'
import { getAdminUsers } from 'pubsweet-component-faraday-selectors'
import {
Row,
Text,
Item,
Label,
OpenModal,
Pagination,
ActionLink,
withFetching,
withPagination,
} from 'pubsweet-component-faraday-ui'
import { AddUser } from './'
import { updateUserStatus, onSubmit } from './utils'
const Users = ({
page,
users,
theme,
history,
journal,
getUsers,
isFetching,
getUserRoles,
itemsPerPage,
deactivateUser,
getStatusLabel,
paginatedItems,
toggleUserStatus,
...rest
}) => (
<Fragment>
<Row alignItems="center" justify="space-between" mb={1}>
<Item alignItems="center">
<ActionLink icon="arrow-left" mr={2} onClick={history.goBack}>
Admin Dashboard
</ActionLink>
<AddUser
form="add-user"
getUsers={getUsers}
modalKey="addUser"
onSubmit={onSubmit}
/>
</Item>
<Pagination {...rest} itemsPerPage={itemsPerPage} page={page} />
</Row>
<Table>
<thead>
<tr>
<th>
<Label>Full Name</Label>
</th>
<th colSpan={2}>
<Label>Email</Label>
</th>
<th>
<Label>Affiliation</Label>
</th>
<th>
<Label>Roles</Label>
</th>
<th>
<Label>Status</Label>
</th>
<th> </th>
</tr>
</thead>
<tbody>
{paginatedItems.map(user => (
<UserRow key={user.id}>
<td>
<Text pl={1}>{`${get(user, 'firstName', '')} ${get(
user,
'lastName',
'',
)}`}</Text>
</td>
<td colSpan={2}>
<Text>{user.email}</Text>
</td>
<td>
<Text>{user.affiliation}</Text>
</td>
<td>
<Text customId>{getUserRoles(user)}</Text>
</td>
<td>
<Text secondary>{getStatusLabel(user)}</Text>
</td>
<HiddenCell>
<Item alignItems="center" justify="flex-end">
<AddUser
edit
getUsers={getUsers}
modalKey={`edit-${user.id}`}
onSubmit={onSubmit}
user={user}
/>
<OpenModal
isFetching={isFetching}
modalKey={`deactivate-${user.id}`}
onConfirm={deactivateUser(user)}
subtitle={`${user.firstName} ${user.lastName}`}
title={`Are you sure to ${
!user.isActive ? 'activate' : 'deactivate'
} user?`}
>
{showModal => (
<ActivateButton
ml={1}
mr={1}
onClick={showModal}
size="small"
>
{!user.isActive ? 'ACTIVATE' : 'DEACTIVATE'}
</ActivateButton>
)}
</OpenModal>
</Item>
</HiddenCell>
</UserRow>
))}
</tbody>
</Table>
</Fragment>
)
export default compose(
ConnectPage(() => [actions.getUsers()]),
connect(
state => ({
items: getAdminUsers(state),
}),
{
getUsers: actions.getUsers,
},
),
withJournal,
withFetching,
withPagination,
withProps(({ journal: { roles = {} } }) => ({
roles: Object.keys(roles),
})),
withHandlers({
getStatusLabel: () => ({ isConfirmed, isActive = true }) => {
if (!isActive) {
return 'INACTIVE'
}
return isConfirmed ? 'ACTIVE' : 'INVITED'
},
deactivateUser: ({ setFetching, getUsers }) => user => ({
hideModal,
setModalError,
}) => {
setFetching(true)
updateUserStatus(user)
.then(() => {
setFetching(false)
getUsers()
hideModal()
})
.catch(() => {
setFetching(false)
setModalError('Something went wrong...')
})
},
getUserRoles: ({ journal: { roles = {} } }) => user => {
const parsedRoles = Object.entries(roles)
.reduce((acc, role) => (user[role[0]] ? [...acc, role[1]] : acc), [])
.join(', ')
return parsedRoles || 'Author'
},
}),
)(Users)
// #region styled-components
const Table = styled.table`
border-collapse: collapse;
& th,
& td {
border: none;
text-align: start;
vertical-align: middle;
height: calc(${th('gridUnit')} * 5);
}
`
const HiddenCell = styled.td`
opacity: 0;
`
const UserRow = styled.tr`
background-color: ${th('colorBackgroundHue2')};
border-bottom: 1px solid ${th('colorBorder')};
&:hover {
background-color: ${th('colorBackgroundHue3')};
${HiddenCell} {
opacity: 1;
}
}
`
const ActivateButton = styled(Button)`
width: 90px;
`
// #endregion