mirror of
https://github.com/yu-i-i/overleaf-cep.git
synced 2026-11-15 14:43:46 +01:00
Revert "Revert "Group SSO - Adding a bug fix for sending emails"" (#15307)
* Revert "Revert "Group SSO - Adding a bug fix for sending emails"" * adding conditional rendering of columns and styling fixes for each render mode with some cypress test GitOrigin-RevId: 168011503ffacff61c8f37bee4c4bfb012909c1f
This commit is contained in:
@@ -17,9 +17,14 @@ const EmailHelper = require('../Helpers/EmailHelper')
|
|||||||
const { csvAttachment } = require('../../infrastructure/Response')
|
const { csvAttachment } = require('../../infrastructure/Response')
|
||||||
const { UserIsManagerError } = require('./UserMembershipErrors')
|
const { UserIsManagerError } = require('./UserMembershipErrors')
|
||||||
const CSVParser = require('json2csv').Parser
|
const CSVParser = require('json2csv').Parser
|
||||||
|
const SSOConfigManager = require('../../../../modules/managed-users/app/src/SSOConfigManager')
|
||||||
|
|
||||||
async function manageGroupMembers(req, res, next) {
|
async function manageGroupMembers(req, res, next) {
|
||||||
const { entity, entityConfig } = req
|
const { entity, entityConfig } = req
|
||||||
|
|
||||||
|
const ssoConfig = await SSOConfigManager.promises.getSSOConfig(
|
||||||
|
entity.ssoConfig
|
||||||
|
)
|
||||||
return entity.fetchV1Data(function (error, entity) {
|
return entity.fetchV1Data(function (error, entity) {
|
||||||
if (error != null) {
|
if (error != null) {
|
||||||
return next(error)
|
return next(error)
|
||||||
@@ -37,12 +42,14 @@ async function manageGroupMembers(req, res, next) {
|
|||||||
if (entityConfig.fields.name) {
|
if (entityConfig.fields.name) {
|
||||||
entityName = entity[entityConfig.fields.name]
|
entityName = entity[entityConfig.fields.name]
|
||||||
}
|
}
|
||||||
|
|
||||||
return res.render('user_membership/group-members-react', {
|
return res.render('user_membership/group-members-react', {
|
||||||
name: entityName,
|
name: entityName,
|
||||||
groupId: entityPrimaryKey,
|
groupId: entityPrimaryKey,
|
||||||
users,
|
users,
|
||||||
groupSize: entity.membersLimit,
|
groupSize: entity.membersLimit,
|
||||||
managedUsersActive: entity.groupPolicy != null,
|
managedUsersActive: entity.groupPolicy != null,
|
||||||
|
groupSSOActive: ssoConfig?.enabled,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ block append meta
|
|||||||
meta(name="ol-groupName", data-type="string", content=name)
|
meta(name="ol-groupName", data-type="string", content=name)
|
||||||
meta(name="ol-groupSize", data-type="json", content=groupSize)
|
meta(name="ol-groupSize", data-type="json", content=groupSize)
|
||||||
meta(name="ol-managedUsersActive", data-type="boolean", content=managedUsersActive)
|
meta(name="ol-managedUsersActive", data-type="boolean", content=managedUsersActive)
|
||||||
|
meta(name="ol-groupSSOActive", data-type="boolean", content=groupSSOActive)
|
||||||
|
|
||||||
block content
|
block content
|
||||||
main.content.content-alt#subscription-manage-group-root
|
main.content.content-alt#subscription-manage-group-root
|
||||||
|
|||||||
@@ -1058,6 +1058,7 @@
|
|||||||
"sort_by_x": "",
|
"sort_by_x": "",
|
||||||
"source": "",
|
"source": "",
|
||||||
"spell_check": "",
|
"spell_check": "",
|
||||||
|
"sso": "",
|
||||||
"sso_config_prop_help_certificate": "",
|
"sso_config_prop_help_certificate": "",
|
||||||
"sso_config_prop_help_first_name": "",
|
"sso_config_prop_help_first_name": "",
|
||||||
"sso_config_prop_help_last_name": "",
|
"sso_config_prop_help_last_name": "",
|
||||||
@@ -1075,7 +1076,9 @@
|
|||||||
"sso_is_enabled_explanation_1": "",
|
"sso_is_enabled_explanation_1": "",
|
||||||
"sso_is_enabled_explanation_2": "",
|
"sso_is_enabled_explanation_2": "",
|
||||||
"sso_link_error": "",
|
"sso_link_error": "",
|
||||||
|
"sso_linked": "",
|
||||||
"sso_logs": "",
|
"sso_logs": "",
|
||||||
|
"sso_unlinked": "",
|
||||||
"start_a_free_trial": "",
|
"start_a_free_trial": "",
|
||||||
"start_by_adding_your_email": "",
|
"start_by_adding_your_email": "",
|
||||||
"start_free_trial": "",
|
"start_free_trial": "",
|
||||||
|
|||||||
+12
-2
@@ -6,8 +6,10 @@ import Badge from '../../../../shared/components/badge'
|
|||||||
import Tooltip from '../../../../shared/components/tooltip'
|
import Tooltip from '../../../../shared/components/tooltip'
|
||||||
import type { ManagedUserAlert } from '../../utils/types'
|
import type { ManagedUserAlert } from '../../utils/types'
|
||||||
import ManagedUserStatus from './managed-user-status'
|
import ManagedUserStatus from './managed-user-status'
|
||||||
|
import SSOStatus from './sso-status'
|
||||||
import ManagedUserDropdownButton from './managed-user-dropdown-button'
|
import ManagedUserDropdownButton from './managed-user-dropdown-button'
|
||||||
import ManagedUsersSelectUserCheckbox from './managed-users-select-user-checkbox'
|
import ManagedUsersSelectUserCheckbox from './managed-users-select-user-checkbox'
|
||||||
|
import getMeta from '@/utils/meta'
|
||||||
|
|
||||||
type ManagedUserRowProps = {
|
type ManagedUserRowProps = {
|
||||||
user: User
|
user: User
|
||||||
@@ -23,6 +25,7 @@ export default function ManagedUserRow({
|
|||||||
groupId,
|
groupId,
|
||||||
}: ManagedUserRowProps) {
|
}: ManagedUserRowProps) {
|
||||||
const { t } = useTranslation()
|
const { t } = useTranslation()
|
||||||
|
const groupSSOActive = getMeta('ol-groupSSOActive')
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<tr
|
<tr
|
||||||
@@ -30,7 +33,7 @@ export default function ManagedUserRow({
|
|||||||
className={`managed-user-row ${user.invite ? 'text-muted' : ''}`}
|
className={`managed-user-row ${user.invite ? 'text-muted' : ''}`}
|
||||||
>
|
>
|
||||||
<ManagedUsersSelectUserCheckbox user={user} />
|
<ManagedUsersSelectUserCheckbox user={user} />
|
||||||
<td className="cell-email">
|
<td className={groupSSOActive ? 'cell-email-with-sso-col' : 'cell-email'}>
|
||||||
<span>
|
<span>
|
||||||
{user.email}
|
{user.email}
|
||||||
{user.invite ? (
|
{user.invite ? (
|
||||||
@@ -73,7 +76,14 @@ export default function ManagedUserRow({
|
|||||||
? moment(user.last_active_at).format('Do MMM YYYY')
|
? moment(user.last_active_at).format('Do MMM YYYY')
|
||||||
: 'N/A'}
|
: 'N/A'}
|
||||||
</td>
|
</td>
|
||||||
<td className="cell-security">
|
{groupSSOActive && (
|
||||||
|
<td className="cell-security">
|
||||||
|
<div className="managed-user-security">
|
||||||
|
<SSOStatus user={user} />
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
)}
|
||||||
|
<td className="cell-managed">
|
||||||
<div className="managed-user-security">
|
<div className="managed-user-security">
|
||||||
<ManagedUserStatus user={user} />
|
<ManagedUserStatus user={user} />
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
+16
-3
@@ -9,6 +9,7 @@ import ManagedUserRow from './managed-user-row'
|
|||||||
import OffboardManagedUserModal from './offboard-managed-user-modal'
|
import OffboardManagedUserModal from './offboard-managed-user-modal'
|
||||||
import ManagedUsersListAlert from './managed-users-list-alert'
|
import ManagedUsersListAlert from './managed-users-list-alert'
|
||||||
import ManagedUsersSelectAllCheckbox from './managed-users-select-all-checkbox'
|
import ManagedUsersSelectAllCheckbox from './managed-users-select-all-checkbox'
|
||||||
|
import getMeta from '@/utils/meta'
|
||||||
|
|
||||||
type ManagedUsersListProps = {
|
type ManagedUsersListProps = {
|
||||||
groupId: string
|
groupId: string
|
||||||
@@ -22,6 +23,7 @@ export default function ManagedUsersList({ groupId }: ManagedUsersListProps) {
|
|||||||
const [managedUserAlert, setManagedUserAlert] =
|
const [managedUserAlert, setManagedUserAlert] =
|
||||||
useState<ManagedUserAlert>(undefined)
|
useState<ManagedUserAlert>(undefined)
|
||||||
const { users } = useGroupMembersContext()
|
const { users } = useGroupMembersContext()
|
||||||
|
const groupSSOActive = getMeta('ol-groupSSOActive')
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
@@ -40,7 +42,13 @@ export default function ManagedUsersList({ groupId }: ManagedUsersListProps) {
|
|||||||
<thead>
|
<thead>
|
||||||
<tr>
|
<tr>
|
||||||
<ManagedUsersSelectAllCheckbox />
|
<ManagedUsersSelectAllCheckbox />
|
||||||
<td className="cell-email">
|
<td
|
||||||
|
className={
|
||||||
|
groupSSOActive
|
||||||
|
? 'cell-email-with-sso-col'
|
||||||
|
: 'cell-email'
|
||||||
|
}
|
||||||
|
>
|
||||||
<span className="header">{t('email')}</span>
|
<span className="header">{t('email')}</span>
|
||||||
</td>
|
</td>
|
||||||
<td className="cell-name">
|
<td className="cell-name">
|
||||||
@@ -60,8 +68,13 @@ export default function ManagedUsersList({ groupId }: ManagedUsersListProps) {
|
|||||||
</span>
|
</span>
|
||||||
</Tooltip>
|
</Tooltip>
|
||||||
</td>
|
</td>
|
||||||
<td className="cell-security">
|
{groupSSOActive && (
|
||||||
<span className="header">{t('security')}</span>
|
<td className="cell-security">
|
||||||
|
<span className="header">{t('security')}</span>
|
||||||
|
</td>
|
||||||
|
)}
|
||||||
|
<td className="cell-managed">
|
||||||
|
<span className="header">{t('managed')}</span>
|
||||||
</td>
|
</td>
|
||||||
<td />
|
<td />
|
||||||
</tr>
|
</tr>
|
||||||
|
|||||||
+7
-1
@@ -1,9 +1,11 @@
|
|||||||
import { useCallback } from 'react'
|
import { useCallback } from 'react'
|
||||||
import { useTranslation } from 'react-i18next'
|
import { useTranslation } from 'react-i18next'
|
||||||
import { useGroupMembersContext } from '../../context/group-members-context'
|
import { useGroupMembersContext } from '../../context/group-members-context'
|
||||||
|
import getMeta from '@/utils/meta'
|
||||||
|
|
||||||
export default function ManagedUsersSelectAllCheckbox() {
|
export default function ManagedUsersSelectAllCheckbox() {
|
||||||
const { t } = useTranslation()
|
const { t } = useTranslation()
|
||||||
|
const groupSSOActive = getMeta('ol-groupSSOActive')
|
||||||
|
|
||||||
const { selectedUsers, users, selectAllNonManagedUsers, unselectAllUsers } =
|
const { selectedUsers, users, selectAllNonManagedUsers, unselectAllUsers } =
|
||||||
useGroupMembersContext()
|
useGroupMembersContext()
|
||||||
@@ -28,7 +30,11 @@ export default function ManagedUsersSelectAllCheckbox() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<td className="cell-checkbox">
|
<td
|
||||||
|
className={
|
||||||
|
groupSSOActive ? 'cell-checkbox-with-sso-col ' : 'cell-checkbox'
|
||||||
|
}
|
||||||
|
>
|
||||||
<label htmlFor="select-all" className="sr-only">
|
<label htmlFor="select-all" className="sr-only">
|
||||||
{t('select_all')}
|
{t('select_all')}
|
||||||
</label>
|
</label>
|
||||||
|
|||||||
+7
-1
@@ -2,6 +2,7 @@ import { useTranslation } from 'react-i18next'
|
|||||||
import type { User } from '../../../../../../types/group-management/user'
|
import type { User } from '../../../../../../types/group-management/user'
|
||||||
import { useGroupMembersContext } from '../../context/group-members-context'
|
import { useGroupMembersContext } from '../../context/group-members-context'
|
||||||
import { useCallback } from 'react'
|
import { useCallback } from 'react'
|
||||||
|
import getMeta from '@/utils/meta'
|
||||||
|
|
||||||
type ManagedUsersSelectUserCheckboxProps = {
|
type ManagedUsersSelectUserCheckboxProps = {
|
||||||
user: User
|
user: User
|
||||||
@@ -11,6 +12,7 @@ export default function ManagedUsersSelectUserCheckbox({
|
|||||||
user,
|
user,
|
||||||
}: ManagedUsersSelectUserCheckboxProps) {
|
}: ManagedUsersSelectUserCheckboxProps) {
|
||||||
const { t } = useTranslation()
|
const { t } = useTranslation()
|
||||||
|
const groupSSOActive = getMeta('ol-groupSSOActive')
|
||||||
const { users, selectedUsers, selectUser, unselectUser } =
|
const { users, selectedUsers, selectUser, unselectUser } =
|
||||||
useGroupMembersContext()
|
useGroupMembersContext()
|
||||||
|
|
||||||
@@ -38,7 +40,11 @@ export default function ManagedUsersSelectUserCheckbox({
|
|||||||
const selected = selectedUsers.includes(user)
|
const selected = selectedUsers.includes(user)
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<td className="cell-checkbox">
|
<td
|
||||||
|
className={
|
||||||
|
groupSSOActive ? 'cell-checkbox-with-sso-col ' : 'cell-checkbox'
|
||||||
|
}
|
||||||
|
>
|
||||||
{/* the next check will hide the `checkbox` but still show the `td` */}
|
{/* the next check will hide the `checkbox` but still show the `td` */}
|
||||||
{user.enrollment?.managedBy ? null : (
|
{user.enrollment?.managedBy ? null : (
|
||||||
<>
|
<>
|
||||||
|
|||||||
+41
@@ -0,0 +1,41 @@
|
|||||||
|
import { useTranslation } from 'react-i18next'
|
||||||
|
import { User } from '../../../../../../types/group-management/user'
|
||||||
|
import MaterialIcon from '@/shared/components/material-icon'
|
||||||
|
|
||||||
|
type SSOStatusProps = {
|
||||||
|
user: User
|
||||||
|
}
|
||||||
|
export default function SSOStatus({ user }: SSOStatusProps) {
|
||||||
|
const { t } = useTranslation()
|
||||||
|
return (
|
||||||
|
<span>
|
||||||
|
{user.invite ? (
|
||||||
|
<span className="security-state-invite-pending">
|
||||||
|
<MaterialIcon
|
||||||
|
type="schedule"
|
||||||
|
category="outlined"
|
||||||
|
accessibilityLabel={t('pending_invite')}
|
||||||
|
/>
|
||||||
|
{t('sso')}
|
||||||
|
</span>
|
||||||
|
) : (
|
||||||
|
<>
|
||||||
|
{user.enrollment?.sso ? (
|
||||||
|
<span className="security-state-managed">
|
||||||
|
<MaterialIcon type="check" accessibilityLabel={t('sso_linked')} />
|
||||||
|
{t('sso')}
|
||||||
|
</span>
|
||||||
|
) : (
|
||||||
|
<span className="security-state-not-managed">
|
||||||
|
<MaterialIcon
|
||||||
|
type="close"
|
||||||
|
accessibilityLabel={t('sso_unlinked')}
|
||||||
|
/>
|
||||||
|
{t('sso')}
|
||||||
|
</span>
|
||||||
|
)}
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -106,10 +106,16 @@
|
|||||||
.cell-checkbox {
|
.cell-checkbox {
|
||||||
width: 5%;
|
width: 5%;
|
||||||
}
|
}
|
||||||
|
.cell-checkbox-with-sso-col {
|
||||||
|
width: 2.5%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-email {
|
.cell-email {
|
||||||
width: 45%;
|
width: 45%;
|
||||||
}
|
}
|
||||||
|
.cell-email-with-sso-col {
|
||||||
|
width: 37%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-name {
|
.cell-name {
|
||||||
width: 15%;
|
width: 15%;
|
||||||
@@ -126,6 +132,13 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.cell-security {
|
.cell-security {
|
||||||
|
width: 10%;
|
||||||
|
overflow-x: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
.cell-managed {
|
||||||
width: 15%;
|
width: 15%;
|
||||||
overflow-x: hidden;
|
overflow-x: hidden;
|
||||||
text-overflow: ellipsis;
|
text-overflow: ellipsis;
|
||||||
@@ -142,9 +155,16 @@
|
|||||||
width: 5%;
|
width: 5%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.cell-checkbox-with-sso-col {
|
||||||
|
width: 2.5%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-email {
|
.cell-email {
|
||||||
width: 34%;
|
width: 34%;
|
||||||
}
|
}
|
||||||
|
.cell-email-with-sso-col {
|
||||||
|
width: 29%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-name {
|
.cell-name {
|
||||||
width: 20%;
|
width: 20%;
|
||||||
@@ -155,6 +175,10 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.cell-security {
|
.cell-security {
|
||||||
|
width: 12%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.cell-managed {
|
||||||
width: 15%;
|
width: 15%;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -168,10 +192,16 @@
|
|||||||
.cell-checkbox {
|
.cell-checkbox {
|
||||||
width: 5%;
|
width: 5%;
|
||||||
}
|
}
|
||||||
|
.cell-checkbox-with-sso-col {
|
||||||
|
width: 2.5%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-email {
|
.cell-email {
|
||||||
width: 43%;
|
width: 43%;
|
||||||
}
|
}
|
||||||
|
.cell-email-with-sso-col {
|
||||||
|
width: 37%;
|
||||||
|
}
|
||||||
|
|
||||||
.cell-name {
|
.cell-name {
|
||||||
width: 20%;
|
width: 20%;
|
||||||
@@ -182,6 +212,10 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.cell-security {
|
.cell-security {
|
||||||
|
width: 10%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.cell-managed {
|
||||||
width: 12%;
|
width: 12%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1628,6 +1628,7 @@
|
|||||||
"source": "Source",
|
"source": "Source",
|
||||||
"spell_check": "Spell check",
|
"spell_check": "Spell check",
|
||||||
"spread_the_word_and_fill_bar": "Spread the word and fill this bar up",
|
"spread_the_word_and_fill_bar": "Spread the word and fill this bar up",
|
||||||
|
"sso": "SSO",
|
||||||
"sso_account_already_linked": "Account already linked to another __appName__ user",
|
"sso_account_already_linked": "Account already linked to another __appName__ user",
|
||||||
"sso_config_prop_help_certificate": "Base64 encoded certificate without whitespace",
|
"sso_config_prop_help_certificate": "Base64 encoded certificate without whitespace",
|
||||||
"sso_config_prop_help_first_name": "Property in SAML assertion to use for first name",
|
"sso_config_prop_help_first_name": "Property in SAML assertion to use for first name",
|
||||||
@@ -1648,8 +1649,10 @@
|
|||||||
"sso_is_enabled_explanation_1": "Group members will <0>only</0> be able to sign in via SSO",
|
"sso_is_enabled_explanation_1": "Group members will <0>only</0> be able to sign in via SSO",
|
||||||
"sso_is_enabled_explanation_2": "If there are any problems with the configuration, only you (as the group administrator) will be able to disable SSO.",
|
"sso_is_enabled_explanation_2": "If there are any problems with the configuration, only you (as the group administrator) will be able to disable SSO.",
|
||||||
"sso_link_error": "Error linking account",
|
"sso_link_error": "Error linking account",
|
||||||
|
"sso_linked": "SSO linked",
|
||||||
"sso_logs": "SSO Logs",
|
"sso_logs": "SSO Logs",
|
||||||
"sso_not_linked": "You have not linked your account to __provider__. Please log in to your account another way and link your __provider__ account via your account settings.",
|
"sso_not_linked": "You have not linked your account to __provider__. Please log in to your account another way and link your __provider__ account via your account settings.",
|
||||||
|
"sso_unlinked": "SSO unlinked",
|
||||||
"sso_user_denied_access": "Cannot log in because __appName__ was not granted access to your __provider__ account. Please try again.",
|
"sso_user_denied_access": "Cannot log in because __appName__ was not granted access to your __provider__ account. Please try again.",
|
||||||
"standard": "Standard",
|
"standard": "Standard",
|
||||||
"start_a_free_trial": "Start a free trial",
|
"start_a_free_trial": "Start a free trial",
|
||||||
|
|||||||
+65
-6
@@ -28,6 +28,10 @@ const CLAIRE_JENNINGS = {
|
|||||||
enrollment: {
|
enrollment: {
|
||||||
managedBy: GROUP_ID,
|
managedBy: GROUP_ID,
|
||||||
enrolledAt: new Date('2023-01-03'),
|
enrolledAt: new Date('2023-01-03'),
|
||||||
|
sso: {
|
||||||
|
providerId: '123',
|
||||||
|
externalId: '123',
|
||||||
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
const PATHS = {
|
const PATHS = {
|
||||||
@@ -37,6 +41,14 @@ const PATHS = {
|
|||||||
exportMembers: `/manage/groups/${GROUP_ID}/members/export`,
|
exportMembers: `/manage/groups/${GROUP_ID}/members/export`,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function mountGroupMembersProvider() {
|
||||||
|
cy.mount(
|
||||||
|
<GroupMembersProvider>
|
||||||
|
<GroupMembers />
|
||||||
|
</GroupMembersProvider>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
describe('group members, with managed users', function () {
|
describe('group members, with managed users', function () {
|
||||||
beforeEach(function () {
|
beforeEach(function () {
|
||||||
cy.window().then(win => {
|
cy.window().then(win => {
|
||||||
@@ -51,12 +63,7 @@ describe('group members, with managed users', function () {
|
|||||||
win.metaAttributesCache.set('ol-groupSize', 10)
|
win.metaAttributesCache.set('ol-groupSize', 10)
|
||||||
win.metaAttributesCache.set('ol-managedUsersActive', true)
|
win.metaAttributesCache.set('ol-managedUsersActive', true)
|
||||||
})
|
})
|
||||||
|
mountGroupMembersProvider()
|
||||||
cy.mount(
|
|
||||||
<GroupMembersProvider>
|
|
||||||
<GroupMembers />
|
|
||||||
</GroupMembersProvider>
|
|
||||||
)
|
|
||||||
})
|
})
|
||||||
|
|
||||||
it('renders the group members page', function () {
|
it('renders the group members page', function () {
|
||||||
@@ -209,3 +216,55 @@ describe('group members, with managed users', function () {
|
|||||||
cy.get('.alert').contains('Sorry, something went wrong')
|
cy.get('.alert').contains('Sorry, something went wrong')
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe('Group members when group SSO is enabled', function () {
|
||||||
|
beforeEach(function () {
|
||||||
|
cy.window().then(win => {
|
||||||
|
win.metaAttributesCache = new Map()
|
||||||
|
win.metaAttributesCache.set('ol-users', [
|
||||||
|
JOHN_DOE,
|
||||||
|
BOBBY_LAPOINTE,
|
||||||
|
CLAIRE_JENNINGS,
|
||||||
|
])
|
||||||
|
win.metaAttributesCache.set('ol-groupId', GROUP_ID)
|
||||||
|
win.metaAttributesCache.set('ol-groupName', 'My Awesome Team')
|
||||||
|
win.metaAttributesCache.set('ol-groupSize', 10)
|
||||||
|
win.metaAttributesCache.set('ol-managedUsersActive', true)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
it('should not display SSO Column when group sso is not enabled', function () {
|
||||||
|
cy.window().then(win => {
|
||||||
|
win.metaAttributesCache.set('ol-groupSSOActive', false)
|
||||||
|
})
|
||||||
|
mountGroupMembersProvider()
|
||||||
|
cy.get('ul.managed-users-list table > tbody').within(() => {
|
||||||
|
cy.get('tr:nth-child(2)').within(() => {
|
||||||
|
cy.contains('bobby.lapointe@test.com')
|
||||||
|
cy.get('.sr-only').contains('SSO unlinked').should('not.exist')
|
||||||
|
})
|
||||||
|
|
||||||
|
cy.get('tr:nth-child(3)').within(() => {
|
||||||
|
cy.contains('claire.jennings@test.com')
|
||||||
|
cy.get('.sr-only').contains('SSO linked').should('not.exist')
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
it('should display SSO Column when group sso is not enabled', function () {
|
||||||
|
cy.window().then(win => {
|
||||||
|
win.metaAttributesCache.set('ol-groupSSOActive', true)
|
||||||
|
})
|
||||||
|
mountGroupMembersProvider()
|
||||||
|
cy.get('ul.managed-users-list table > tbody').within(() => {
|
||||||
|
cy.get('tr:nth-child(2)').within(() => {
|
||||||
|
cy.contains('bobby.lapointe@test.com')
|
||||||
|
cy.get('.sr-only').contains('SSO unlinked')
|
||||||
|
})
|
||||||
|
|
||||||
|
cy.get('tr:nth-child(3)').within(() => {
|
||||||
|
cy.contains('claire.jennings@test.com')
|
||||||
|
cy.get('.sr-only').contains('SSO linked')
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|||||||
+33
-9
@@ -1,9 +1,17 @@
|
|||||||
import ManagedUsersList from '../../../../../../frontend/js/features/group-management/components/managed-users/managed-users-list'
|
import ManagedUsersList from '../../../../../../frontend/js/features/group-management/components/managed-users/managed-users-list'
|
||||||
import { GroupMembersProvider } from '../../../../../../frontend/js/features/group-management/context/group-members-context'
|
import { GroupMembersProvider } from '../../../../../../frontend/js/features/group-management/context/group-members-context'
|
||||||
|
|
||||||
describe('ManagedUsersList', function () {
|
const groupId = 'somegroup'
|
||||||
const groupId = 'somegroup'
|
|
||||||
|
|
||||||
|
function mountManagedUsersList() {
|
||||||
|
cy.mount(
|
||||||
|
<GroupMembersProvider>
|
||||||
|
<ManagedUsersList groupId={groupId} />
|
||||||
|
</GroupMembersProvider>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
describe('ManagedUsersList', function () {
|
||||||
describe('with users', function () {
|
describe('with users', function () {
|
||||||
const users = [
|
const users = [
|
||||||
{
|
{
|
||||||
@@ -32,15 +40,31 @@ describe('ManagedUsersList', function () {
|
|||||||
cy.window().then(win => {
|
cy.window().then(win => {
|
||||||
win.metaAttributesCache.set('ol-users', users)
|
win.metaAttributesCache.set('ol-users', users)
|
||||||
})
|
})
|
||||||
|
mountManagedUsersList()
|
||||||
cy.mount(
|
|
||||||
<GroupMembersProvider>
|
|
||||||
<ManagedUsersList groupId={groupId} />
|
|
||||||
</GroupMembersProvider>
|
|
||||||
)
|
|
||||||
})
|
})
|
||||||
|
|
||||||
it('should render the table headers', function () {
|
it('should render the table headers but not SSO Column', function () {
|
||||||
|
cy.window().then(win => {
|
||||||
|
win.metaAttributesCache.set('ol-groupSSOActive', false)
|
||||||
|
})
|
||||||
|
mountManagedUsersList()
|
||||||
|
cy.get('#managed-users-list-headers').should('exist')
|
||||||
|
|
||||||
|
// Select-all checkbox
|
||||||
|
cy.get('#managed-users-list-headers .select-all').should('exist')
|
||||||
|
|
||||||
|
cy.get('#managed-users-list-headers').contains('Email')
|
||||||
|
cy.get('#managed-users-list-headers').contains('Name')
|
||||||
|
cy.get('#managed-users-list-headers').contains('Last Active')
|
||||||
|
cy.get('#managed-users-list-headers')
|
||||||
|
.contains('Security')
|
||||||
|
.should('not.exist')
|
||||||
|
})
|
||||||
|
it('should render the table headers with SSO Column', function () {
|
||||||
|
cy.window().then(win => {
|
||||||
|
win.metaAttributesCache.set('ol-groupSSOActive', true)
|
||||||
|
})
|
||||||
|
mountManagedUsersList()
|
||||||
cy.get('#managed-users-list-headers').should('exist')
|
cy.get('#managed-users-list-headers').should('exist')
|
||||||
|
|
||||||
// Select-all checkbox
|
// Select-all checkbox
|
||||||
|
|||||||
@@ -69,6 +69,11 @@ describe('UserMembershipController', function () {
|
|||||||
getSessionUser: sinon.stub().returns(this.user),
|
getSessionUser: sinon.stub().returns(this.user),
|
||||||
getLoggedInUserId: sinon.stub().returns(this.user._id),
|
getLoggedInUserId: sinon.stub().returns(this.user._id),
|
||||||
}
|
}
|
||||||
|
this.SSOConfigManager = {
|
||||||
|
promises: {
|
||||||
|
getSSOConfig: sinon.stub().resolves({ enabled: true }),
|
||||||
|
},
|
||||||
|
}
|
||||||
this.UserMembershipHandler = {
|
this.UserMembershipHandler = {
|
||||||
getEntity: sinon.stub().yields(null, this.subscription),
|
getEntity: sinon.stub().yields(null, this.subscription),
|
||||||
createEntity: sinon.stub().yields(null, this.institution),
|
createEntity: sinon.stub().yields(null, this.institution),
|
||||||
@@ -91,6 +96,8 @@ describe('UserMembershipController', function () {
|
|||||||
'../SplitTests/SplitTestHandler': this.SplitTestHandler,
|
'../SplitTests/SplitTestHandler': this.SplitTestHandler,
|
||||||
'./UserMembershipHandler': this.UserMembershipHandler,
|
'./UserMembershipHandler': this.UserMembershipHandler,
|
||||||
'@overleaf/settings': this.Settings,
|
'@overleaf/settings': this.Settings,
|
||||||
|
'../../../../modules/managed-users/app/src/SSOConfigManager':
|
||||||
|
this.SSOConfigManager,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
))
|
))
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
export type UserEnrollment = {
|
export type UserEnrollment = {
|
||||||
managedBy?: string
|
managedBy?: string
|
||||||
enrolledAt?: Date
|
enrolledAt?: Date
|
||||||
|
sso?: object
|
||||||
}
|
}
|
||||||
|
|
||||||
export type User = {
|
export type User = {
|
||||||
|
|||||||
Reference in New Issue
Block a user