Skip to content
This repository was archived by the owner on Sep 11, 2024. It is now read-only.

Commit e48110d

Browse files
authored
Move the account management button (#12663)
* Disable profile controls if the HS doesn't allow them to be set Also updates to the js-sdk interface changes in matrix-org/matrix-js-sdk#4246 * Remove unnecessary await * Pass disabled prop to accessiblebutton in avatarsetting * Move the account management button The section it lives in with the server name goes, and the button just lives on its own in the profile section. * Update test * Revert bits of previous PR that are no longer wanted because we squash merge so git can no longer make sense of what changes have been applied. * More squash-merge fails * More more squash merge fails
1 parent 1fbc972 commit e48110d

File tree

5 files changed

+46
-36
lines changed

5 files changed

+46
-36
lines changed

res/css/views/settings/_UserProfileSettings.pcss

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,15 @@ limitations under the License.
4747
font-size: 15px;
4848
font-weight: 500;
4949
}
50+
51+
.mx_UserProfileSettings_profile_buttons {
52+
margin-top: var(--cpd-space-8x);
53+
margin-bottom: var(--cpd-space-8x);
54+
}
55+
56+
.mx_UserProfileSettings_accountmanageIcon {
57+
margin-right: var(--cpd-space-2x);
58+
}
5059
}
5160

5261
@media (max-width: 768px) {

src/components/views/settings/UserProfileSettings.tsx

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ limitations under the License.
1717
import React, { ChangeEvent, useCallback, useEffect, useMemo, useState } from "react";
1818
import { logger } from "matrix-js-sdk/src/logger";
1919
import { EditInPlace, Alert, ErrorMessage } from "@vector-im/compound-web";
20+
import { Icon as PopOutIcon } from "@vector-im/compound-design-tokens/icons/pop-out.svg";
2021

2122
import { _t } from "../../../languageHandler";
2223
import { OwnProfileStore } from "../../../stores/OwnProfileStore";
@@ -29,6 +30,7 @@ import UserIdentifierCustomisations from "../../../customisations/UserIdentifier
2930
import { useId } from "../../../utils/useId";
3031
import CopyableText from "../elements/CopyableText";
3132
import { useMatrixClientContext } from "../../../contexts/MatrixClientContext";
33+
import AccessibleButton from "../elements/AccessibleButton";
3234

3335
const SpinnerToast: React.FC = ({ children }) => (
3436
<>
@@ -55,7 +57,28 @@ const UsernameBox: React.FC<UsernameBoxProps> = ({ username }) => {
5557
);
5658
};
5759

60+
interface ManageAccountButtonProps {
61+
externalAccountManagementUrl: string;
62+
}
63+
64+
const ManageAccountButton: React.FC<ManageAccountButtonProps> = ({ externalAccountManagementUrl }) => (
65+
<AccessibleButton
66+
onClick={null}
67+
element="a"
68+
kind="primary"
69+
target="_blank"
70+
rel="noreferrer noopener"
71+
href={externalAccountManagementUrl}
72+
data-testid="external-account-management-link"
73+
>
74+
<PopOutIcon className="mx_UserProfileSettings_accountmanageIcon" width="24" height="24" />
75+
{_t("settings|general|oidc_manage_button")}
76+
</AccessibleButton>
77+
);
78+
5879
interface UserProfileSettingsProps {
80+
// The URL to redirect the user to in order to manage their account.
81+
externalAccountManagementUrl?: string;
5982
// Whether the homeserver allows the user to set their display name.
6083
canSetDisplayName: boolean;
6184
// Whether the homeserver allows the user to set their avatar.
@@ -65,7 +88,11 @@ interface UserProfileSettingsProps {
6588
/**
6689
* A group of settings views to allow the user to set their profile information.
6790
*/
68-
const UserProfileSettings: React.FC<UserProfileSettingsProps> = ({ canSetDisplayName, canSetAvatar }) => {
91+
const UserProfileSettings: React.FC<UserProfileSettingsProps> = ({
92+
externalAccountManagementUrl,
93+
canSetDisplayName,
94+
canSetAvatar,
95+
}) => {
6996
const [avatarURL, setAvatarURL] = useState(OwnProfileStore.instance.avatarMxc);
7097
const [displayName, setDisplayName] = useState(OwnProfileStore.instance.displayName ?? "");
7198
const [avatarError, setAvatarError] = useState<boolean>(false);
@@ -192,6 +219,11 @@ const UserProfileSettings: React.FC<UserProfileSettingsProps> = ({ canSetDisplay
192219
</Alert>
193220
)}
194221
{userIdentifier && <UsernameBox username={userIdentifier} />}
222+
{externalAccountManagementUrl && (
223+
<div className="mx_UserProfileSettings_profile_buttons">
224+
<ManageAccountButton externalAccountManagementUrl={externalAccountManagementUrl} />
225+
</div>
226+
)}
195227
</div>
196228
);
197229
};

src/components/views/settings/tabs/user/GeneralUserSettingsTab.tsx

Lines changed: 1 addition & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -215,41 +215,13 @@ export default class GeneralUserSettingsTab extends React.Component<IProps, ISta
215215
);
216216
}
217217

218-
let externalAccountManagement: JSX.Element | undefined;
219-
if (this.state.externalAccountManagementUrl) {
220-
const { hostname } = new URL(this.state.externalAccountManagementUrl);
221-
222-
externalAccountManagement = (
223-
<>
224-
<SettingsSubsectionText data-testid="external-account-management-outer">
225-
{_t(
226-
"settings|general|external_account_management",
227-
{ hostname },
228-
{ code: (sub) => <code>{sub}</code> },
229-
)}
230-
</SettingsSubsectionText>
231-
<AccessibleButton
232-
onClick={null}
233-
element="a"
234-
kind="primary"
235-
target="_blank"
236-
rel="noreferrer noopener"
237-
href={this.state.externalAccountManagementUrl}
238-
data-testid="external-account-management-link"
239-
>
240-
{_t("settings|general|oidc_manage_button")}
241-
</AccessibleButton>
242-
</>
243-
);
244-
}
245218
return (
246219
<>
247220
<SettingsSubsection
248221
heading={_t("settings|general|account_section")}
249222
stretchContent
250223
data-testid="accountSection"
251224
>
252-
{externalAccountManagement}
253225
{passwordChangeSection}
254226
</SettingsSubsection>
255227
</>
@@ -324,6 +296,7 @@ export default class GeneralUserSettingsTab extends React.Component<IProps, ISta
324296
<SettingsTab data-testid="mx_GeneralUserSettingsTab">
325297
<SettingsSection>
326298
<UserProfileSettings
299+
externalAccountManagementUrl={this.state.externalAccountManagementUrl}
327300
canSetDisplayName={this.state.canSetDisplayName}
328301
canSetAvatar={this.state.canSetAvatar}
329302
/>

src/i18n/strings/en_EN.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2511,7 +2511,6 @@
25112511
"error_revoke_msisdn_discovery": "Unable to revoke sharing for phone number",
25122512
"error_share_email_discovery": "Unable to share email address",
25132513
"error_share_msisdn_discovery": "Unable to share phone number",
2514-
"external_account_management": "Your account details are managed separately at <code>%(hostname)s</code>.",
25152514
"identity_server_no_token": "No identity access token found",
25162515
"identity_server_not_set": "Identity server not set",
25172516
"incorrect_msisdn_verification": "Incorrect verification code",

test/components/views/settings/tabs/user/GeneralUserSettingsTab-test.tsx

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -92,13 +92,10 @@ describe("<GeneralUserSettingsTab />", () => {
9292
} as unknown as OidcClientStore;
9393
jest.spyOn(stores, "oidcClientStore", "get").mockReturnValue(mockOidcClientStore);
9494

95-
const { getByTestId } = render(getComponent());
95+
render(getComponent());
9696

97-
// wait for well-known call to settle
98-
await flushPromises();
99-
100-
expect(getByTestId("external-account-management-outer").textContent).toMatch(/.*id\.server\.org/);
101-
expect(getByTestId("external-account-management-link").getAttribute("href")).toMatch(accountManagementLink);
97+
const manageAccountLink = await screen.findByRole("button", { name: "Manage account" });
98+
expect(manageAccountLink.getAttribute("href")).toMatch(accountManagementLink);
10299
});
103100

104101
describe("Manage integrations", () => {

0 commit comments

Comments
 (0)