Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 11 additions & 2 deletions client/components/mma/dataPrivacy/CookiesOnTheBrowserSection.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,17 @@ export const CookiesOnThisBrowserSection = (
When we make the Guardian available for you online, we use
cookies and similar technologies to help us to do this. Some are
necessary to help our website work properly and can’t be
switched off, and some are optional but may support the Guardian
and your experience in other ways.
switched off, and some are optional but may support your
experience in other ways or help support the Guardian, including
through personalised advertising.
</p>
<p css={dataPrivacyParagraphCss}>
If you read the Guardian ad free or subscribe to Guardian
Ad-Lite, you can manage the use of cookies on our site for
personalised advertising, and disable the sharing of data with
partners for personalised advertising purposes by clicking below
or on the "Privacy settings" link in the footer of every page of
our site.
</p>
<Button
disabled={false}
Expand Down
86 changes: 1 addition & 85 deletions client/components/mma/dataPrivacy/DataPrivacyPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,44 +2,14 @@ import type { CMP } from '@guardian/libs';
import { from } from '@guardian/source/foundations';
import { useEffect, useState } from 'react';
import { gridItemPlacement } from '../../../styles/grid';
import { fetchWithDefaultParameters } from '../../../utilities/fetch';
import {
LoadingState,
useAsyncLoader,
} from '../../../utilities/hooks/useAsyncLoader';
import { GenericErrorScreen } from '../../shared/GenericErrorScreen';
import { WithStandardTopMargin } from '../../shared/WithStandardTopMargin';
import * as UserAPI from '../identity/idapi/user';
import { ConsentOptions, mapSubscriptions } from '../identity/identity';
import { Lines } from '../identity/Lines';
import type { ConsentOption } from '../identity/models';
import { Actions, useConsentOptions } from '../identity/useConsentOptions';
import { JsonResponseHandler } from '../shared/asyncComponents/DefaultApiResponseHandler';
import { DefaultLoadingView } from '../shared/asyncComponents/DefaultLoadingView';
import { CookiesOnThisBrowserSection } from './CookiesOnTheBrowserSection';
import { dataPrivacyWrapper } from './DataPrivacy.styles';
import { LearnMoreSection } from './LearnMoreSection';
import { YourDataSection } from './YourDataSection';

type DataPrivacyResponse = [ConsentOption[], UserAPI.UserAPIResponse];

const dataPrivacyFetcher = () =>
Promise.all([
fetchWithDefaultParameters('/idapi/consents'),
fetchWithDefaultParameters('/idapi/user'),
]);

export const DataPrivacyPage = () => {
const { options, error, subscribe, unsubscribe } = Actions;
const [state, dispatch] = useConsentOptions();
const [importedCmp, setImportedCmp] = useState<CMP | null>(null);
const {
data: dataPrivacyResponse,
loadingState,
}: {
data: DataPrivacyResponse | null;
loadingState: LoadingState;
} = useAsyncLoader(dataPrivacyFetcher, JsonResponseHandler);

/**
* This function imports and loads the cmp app to the state value, importedCmp
Expand All @@ -51,58 +21,9 @@ export const DataPrivacyPage = () => {
});
};

const consents = ConsentOptions.consents(state.options);

useEffect(() => {
if (dataPrivacyResponse) {
/**
* Use the response from the dataPrivacyFetcher api call
* to get the users subscriptions/consents and dispatch the options to the
* store.
*/
const [consentOptions, userResponse] = dataPrivacyResponse;
const user = UserAPI.toUser(userResponse);
const consentOpt = mapSubscriptions(user.consents, consentOptions);
dispatch(options(consentOpt));
}
loadCMP();
}, [dataPrivacyResponse, dispatch, options]);

if (loadingState == LoadingState.HasError) {
return <GenericErrorScreen />;
}
if (loadingState == LoadingState.IsLoading) {
return (
<DefaultLoadingView loadingMessage="Loading your privacy details." />
);
}
if (dataPrivacyResponse === null) {
return <GenericErrorScreen />;
}

/**
* This function makes an API request to /users/me/consents to subscribe or unsubscribe.
* It then dispatches a redux action
*
* @param {string} id
*/
const toggleConsentSubscription = async (id: string) => {
const option = ConsentOptions.findById(state.options, id);
try {
if (option === undefined) {
throw Error('Id not found');
}
if (option.subscribed) {
await ConsentOptions.unsubscribe(option);
dispatch(unsubscribe(id));
} else {
await ConsentOptions.subscribe(option);
dispatch(subscribe(id));
}
} catch (e) {
dispatch(error(e));
}
};
}, [importedCmp]);

/**
* This function triggers importedCmp?.showPrivacyManage
Expand Down Expand Up @@ -135,11 +56,6 @@ export const DataPrivacyPage = () => {
}}
>
<WithStandardTopMargin>
<YourDataSection
consents={consents}
toggleConsent={toggleConsentSubscription}
/>
<Lines n={1} />
<CookiesOnThisBrowserSection onClick={openManageCookies} />
<Lines n={1} />
<LearnMoreSection />
Expand Down
4 changes: 3 additions & 1 deletion client/components/mma/dataPrivacy/LearnMoreSection.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,9 @@ export const LearnMoreSection = () => {
</h3>

<p css={dataPrivacyParagraphCss}>
For more information about how we use your data, visit our&nbsp;
For more information about how we use your data, including the
generation of random identifiers based on your email address for
advertising and marketing, visit our&nbsp;
<a
css={aCss}
target="_blank"
Expand Down
Loading