Fetch and display campaigns with wp.data.

This commit is contained in:
Gan Eng Chin 2023-02-01 19:02:03 +08:00
parent 630bd0ab17
commit cd7b5f2c96
No known key found for this signature in database
GPG Key ID: 94D5D972860ADB01
8 changed files with 134 additions and 95 deletions

View File

@ -7,4 +7,6 @@ export const TYPES = {
'RECEIVE_RECOMMENDED_CHANNELS_SUCCESS' as const,
RECEIVE_RECOMMENDED_CHANNELS_ERROR:
'RECEIVE_RECOMMENDED_CHANNELS_ERROR' as const,
RECEIVE_CAMPAIGNS_SUCCESS: 'RECEIVE_CAMPAIGNS_SUCCESS' as const,
RECEIVE_CAMPAIGNS_ERROR: 'RECEIVE_CAMPAIGNS_ERROR' as const,
};

View File

@ -2,7 +2,12 @@
* Internal dependencies
*/
import { TYPES } from './action-types';
import { ApiFetchError, RegisteredChannel, RecommendedChannel } from './types';
import {
ApiFetchError,
RegisteredChannel,
RecommendedChannel,
Campaign,
} from './types';
export const receiveRegisteredChannelsSuccess = (
channels: Array< RegisteredChannel >
@ -38,9 +43,26 @@ export const receiveRecommendedChannelsError = ( error: ApiFetchError ) => {
};
};
export const receiveCampaignsSuccess = ( campaigns: Array< Campaign > ) => {
return {
type: TYPES.RECEIVE_CAMPAIGNS_SUCCESS,
payload: campaigns,
};
};
export const receiveCampaignsError = ( error: ApiFetchError ) => {
return {
type: TYPES.RECEIVE_CAMPAIGNS_ERROR,
payload: error,
error: true,
};
};
export type Action = ReturnType<
| typeof receiveRegisteredChannelsSuccess
| typeof receiveRegisteredChannelsError
| typeof receiveRecommendedChannelsSuccess
| typeof receiveRecommendedChannelsError
| typeof receiveCampaignsSuccess
| typeof receiveCampaignsError
>;

View File

@ -20,6 +20,10 @@ const initialState = {
data: undefined,
error: undefined,
},
campaigns: {
data: undefined,
error: undefined,
},
};
export const reducer: Reducer< State, Action > = (
@ -55,6 +59,23 @@ export const reducer: Reducer< State, Action > = (
error: action.payload,
},
};
case TYPES.RECEIVE_CAMPAIGNS_SUCCESS:
return {
...state,
campaigns: {
data: action.payload,
},
};
case TYPES.RECEIVE_CAMPAIGNS_ERROR:
return {
...state,
campaigns: {
error: action.payload,
},
};
default:
return state;
}

View File

@ -11,8 +11,10 @@ import {
receiveRegisteredChannelsError,
receiveRecommendedChannelsSuccess,
receiveRecommendedChannelsError,
receiveCampaignsSuccess,
receiveCampaignsError,
} from './actions';
import { RegisteredChannel, RecommendedChannel } from './types';
import { RegisteredChannel, RecommendedChannel, Campaign } from './types';
import { API_NAMESPACE } from './constants';
import { isApiFetchError } from './guards';
@ -47,3 +49,19 @@ export function* getRecommendedChannels() {
throw error;
}
}
export function* getCampaigns() {
try {
const data: Array< Campaign > = yield apiFetch( {
path: `${ API_NAMESPACE }/campaigns`,
} );
yield receiveCampaignsSuccess( data );
} catch ( error ) {
if ( isApiFetchError( error ) ) {
yield receiveCampaignsError( error );
}
throw error;
}
}

View File

@ -10,3 +10,7 @@ export const getRegisteredChannels = ( state: State ) => {
export const getRecommendedChannels = ( state: State ) => {
return state.recommendedChannels;
};
export const getCampaigns = ( state: State ) => {
return state.campaigns;
};

View File

@ -50,7 +50,24 @@ export type RecommendedChannelsState = {
error?: ApiFetchError;
};
export type Campaign = {
id: string;
channel: string;
title: string;
manage_url: string;
cost: {
value: string;
currency: string;
};
};
export type CampaignsState = {
data?: Array< Campaign >;
error?: ApiFetchError;
};
export type State = {
registeredChannels: ChannelsState;
recommendedChannels: RecommendedChannelsState;
campaigns: CampaignsState;
};

View File

@ -41,6 +41,11 @@ export const Campaigns = () => {
);
}
// TODO: error message here.
if ( ! data ) {
return <div>error</div>;
}
if ( data.length === 0 ) {
return (
<Card className="woocommerce-marketing-campaigns-card">

View File

@ -1,104 +1,54 @@
/**
* External dependencies
*/
import { useSelect } from '@wordpress/data';
/**
* Internal dependencies
*/
import { Campaign } from '~/marketing/types';
import { STORE_KEY } from '~/marketing/data-multichannel/constants';
import {
CampaignsState,
Campaign as APICampaign,
ApiFetchError,
} from '~/marketing/data-multichannel/types';
import { useRegisteredChannels } from '~/marketing/hooks';
type UseCampaignsType = {
loading: boolean;
data: Array< Campaign >;
data?: Array< Campaign >;
error?: ApiFetchError;
};
// // TODO: testing for loading state.
// export const useCampaigns = (): UseCampaignsType => {
// return {
// loading: true,
// data: [],
// };
// };
// TODO: testing for empty data.
// export const useCampaigns = (): UseCampaignsType => {
// return {
// loading: false,
// data: [],
// };
// };
// TODO: testing with campaigns data.
export const useCampaigns = (): UseCampaignsType => {
return {
loading: false,
data: [
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-01',
title: 'Performance Max 01',
description: 'New Zealand',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-02',
title: 'Performance Max 02',
description: '6 countries',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-03',
title: 'Performance Max 03',
description: '10 countries • 15 Sep - 31 Oct 2022',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-04',
title: 'Performance Max 04',
description: 'New Zealand',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-05',
title: 'Performance Max 05',
description: 'New Zealand',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-06',
title: 'Performance Max 06',
description: 'New Zealand',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
{
channelSlug: 'google-listings-and-ads',
channelName: 'Google Listings and Ads',
icon: 'https://woocommerce.com/wp-content/plugins/wccom-plugins/marketing-tab-rest-api/icons/google.svg',
id: 'gla-campaign-07',
title: 'Performance Max 07',
description: 'New Zealand',
cost: '$50',
manageUrl: 'https://www.google.com/manage-campaign',
},
],
};
const { data } = useRegisteredChannels();
return useSelect( ( select ) => {
const { hasFinishedResolution, getCampaigns } = select( STORE_KEY );
const campaignsState = getCampaigns< CampaignsState >();
const convert = ( campaign: APICampaign ): Campaign => {
const channel = data?.find(
( el ) => el.slug === campaign.channel
);
return {
id: `${ campaign.channel }|${ campaign.id }`,
title: campaign.title,
description: '',
cost: `${ campaign.cost.currency } ${ campaign.cost.value }`,
manageUrl: campaign.manage_url,
icon: channel?.icon || '',
channelName: channel?.title || '',
channelSlug: campaign.channel,
};
};
return {
loading: ! hasFinishedResolution( 'getCampaigns' ),
data: campaignsState.data?.map( convert ),
error: campaignsState.error,
};
} );
};