ShoppingGives SDK
The ShoppingGives SDK (SG SDK) provides the necessary methods for developing custom experiences by facilitating the development of custom widgets or UI components built by our clients using any Javascript-based framework (such as REACT, Angular, or Vue). The SG SDK provides the data needed to power a custom UI. This SG SDK does not provide UI elements, only the data needed to power a custom UI.
Built With
Prerequisites
To use the SG SDK, you will need a ShoppingGives store ID (contact your ShoppingGives account manager).
Getting Started
Installation
npm install @shoppinggivesos/impact-sdk
Usage
The first thing you need to do after installing the package is select the type of "context" you want to set up. We currently support two types of context: Cart
and Product
. If you plan to use the SG SDK to power a custom experience on the product page, then you need to use the ProductHandler
. Likewise, if you plan to power a custom experience on the cart page, use the CartHandler
.
import { CartHandler, Environments } from '@shoppinggivesos/impact-sdk';
const config = {
storeId: '00000000-0000-0000-0000-000000000000', // Shoppinggives store ID
environment: Environments.Production, // Shoppinggives store environment for most people
// you will select Environments.Production here.
// If you receive a Staging store ID from your account manager,
// use the Environments.Staging value
testMode: false, // Sets the tracking to be test purchases that do not create a real donation!
logger: {
error: (message) => {},
debug: (message) => {},
warn: (message) => {},
}, // Optional: Custom logging implementation,
// if you omit this param the SG SDK uses console.log by default.
persistence: {
get: (key) => {},
set: (key, value) => {},
delete: (key) => {},
}, // Optional: Custom persistence cache implementation,
// if you omit this param the SG SDK uses session storage by default.
};
// bootstrap the client
const client = new CartHandler(config);
// register any events if you want to use the event system vs
// async / awaiting the methods. (more information can be found below)
// events need to be registered before the initialize method is called.
client.on('SDK::Ready', (data) => {
// handle SDK::Ready event
});
// initialize the client with current cart state
const data = await client.initialize({
cartTotal: 10, // Current cart total
lineItems: [], // All current line items in the cart or an empty array if no items are in the cart.
discount: 0, // The discount applied to the cart if any is set. This is the $ amount
// not the % percentage.
});
Handling Updates
We support two main ways to work with the SG SDK.
- All public-facing methods return promises so that you can use
async / await
orthen / catch
to retrieve the returned data. For example:
async / await
const results = await client.search('Happys Porch', 0, 25);
then / catch
let results = [];
client
.search('Homes For Our Troops', 0, 25)
.then((data) => {
results = data;
})
.catch((error) => {});
- Alternatively, we have an events system. You can subscribe to the events and handle changes with callback functions.
Event Type | Description |
---|---|
SDK::Ready | Emitted when the SG SDK has completed all necessary initialization steps and is ready to accept requests from the client. This typically includes loading any necessary resources and establishing a connection to the server. |
SDK::Error | Emitted when an error occurs inside the SG SDK, it contains a type property that dictates the type of error so you can handle it accordingly. |
SDK::Updated | Emitted when the SG SDK has finished re-calculating the donation based on the new data. |
Cause::Updated | Emitted when our backend has confirmed the new cause was successfully updated. |
Search::Finished | Emitted when the call to the search ShoppingGives API is finished. |
Example:
client.on('Cause::Updated', (data) => {
// handle the updating of the selected cause
});
Handling Errors
We provide two systems for dealing with errors in the SG SDK. By default, the SG SDK will throw an error you must catch. The other way you can handle errors is by using the SDK::Error
event and set up a callback to handle errors in a centralized place.
The error payload includes a 'type' property that specifies the type of error that occurred. This can be used to distinguish between different types of errors and to tailor your error-handling logic accordingly.
try {
results = await client.search(searchTerm, 0, 25);
} catch (error) {
// handle error based on the type property:
switch (error.type) {
case "ShoppinggivesApiError":
// handle error, hide UI or show error state
break;
case "ShoppinggivesValidationError"
// handle validation error
default:
break;
}
}
Alternatively, you can handle errors by subscribing to the event SDK::Error
, the event is emitted whenever an error occurs inside the SG SDK. This event is intended to provide a mechanism for handling errors that may occur while using the SG SDK so that you can gracefully handle or recover from them in your code.
To handle this event, you can add an event listener that gets called whenever the event is emitted. The event listener function should accept an 'error' parameter containing an instance of an error object with additional information about the error.
Here is an example of how you might handle the SDK::Error
event:
client.on('SDK::Error', (error) => {
switch (error.type) {
case "ShoppinggivesApiError":
// handle error, hide UI or show error state
break;
case "ShoppinggivesValidationError"
// handle validation error
default:
break;
}
});
Methods
Initialize() Product Handler
This function must be called first to initialize the product widget. The response contains everything needed to load the product widget.
Request Body:
Parameter | Type | Required | Description |
---|---|---|---|
cmsId | string | true | Product CMS ID |
price | number | true | Product price |
Response Body:
Property | Type | Description |
---|---|---|
totalDonationAmount | number | Current total donation amount to display on the widget |
showWidget | boolean | Whether or not to show the widget based on store settings or eligibility |
donationBreakdown | DonationRecipientsModel[] | The complete breakdown of causes and their associated donation |
charities | CauseModel[] | Charities associated with the store |
selectedCauses | CauseModel[] | Currently selected causes for donation |
activeCampaigns | ActiveCampaignsModel | Active campaigns on store |
searchEnabled | boolean | Whether the store has search toggled on or off |
letShoppersChoose | boolean | Whether the customer has a choice of charities |
trackingId | string | ID associating supported charity to the user session |
Update() Product Handler
Re-calculates the donation amount based on product changes, i.e., product variant changes.
Request Body:
Parameter | Type | Required | Description |
---|---|---|---|
cmsId | string | true | Product CMS ID |
price | number | true | Product price |
Response Body:
Property | Type | Description |
---|---|---|
totalDonationAmount | number | Current total donation amount to display on the widget |
donationBreakdown | DonationRecipientsModel[] | The complete breakdown of causes and their associated donation |
charities | CauseModel[] | Charities associated with the store |
selectedCauses | CauseModel[] | Currently selected causes for donation |
excluded | boolean | Whether or not the product is excluded from the donation |
Initalize() Cart Handler
This function must be called first to initialize the cart widget. The response contains everything needed to load the cart widget.
Request Body:
Parameter | Type | Required | Description |
---|---|---|---|
lineItems | CmsLineItem[] | true | All line items in the cart |
discount | number | false | Current cart discount |
Response Body:
Property | Type | Description |
---|---|---|
totalDonationAmount | number | Current total donation amount to display on the widget |
showWidget | boolean | Whether or not to show the widget based on store settings or eligibility |
donationBreakdown | DonationRecipientsModel[] | The complete breakdown of causes and their associated donation |
charities | CauseModel[] | Charities associated with the store |
selectedCauses | CauseModel[] | Currently selected causes for donation |
activeCampaigns | ActiveCampaignsModel | Active campaigns on store |
searchEnabled | boolean | Whether the store has search toggled on or off |
letShoppersChoose | boolean | Whether the customer has a choice of charities |
trackingId | string | ID associating supported charity to the user session |
directDonationInCart | boolean | Whether or not there is a direct donation on the cart (roundups/addons) |
Update() Cart Handler
Re-calculates the donation amount based on the cart's item changes.
Request Body:
Parameter | Type | Required | Description |
---|---|---|---|
lineItems | CmsLineItem[] | true | All line items in the cart |
discount | number | false | Current cart discount |
Response Body:
Property | Type | Description |
---|---|---|
totalDonationAmount | number | Current total donation amount to display on the widget |
donationBreakdown | DonationRecipientsModel[] | The complete breakdown of causes and their associated donation |
charities | array[] | Charities associated with the store |
selectedCauses | CauseModel[] | Currently selected causes for donation |
directDonationInCart | boolean | Whether or not there is a direct donation on the cart (roundups/addon) |
Search()
Returns a list of charities based on search parameters.
Request Body:
Parameter | Type | Required | |
---|---|---|---|
skip | number | true | How many entries to skip |
take | number | true | How many entries to take |
searchTerm | string | flase | String being searched |
zip | string | false | Search within a ZIP code |
city | string | false | Search within a city |
state | string | false | Search within a state (Value is the 2 letter state abbreviation) |
category | string | false | Search within a category Category Dictionary[] |
Response Body:
SetCause()
Updates tracking when a user selects a new cause.
Request Body:
Parameter | Type | Required | Description |
---|---|---|---|
cause | CauseModel[] | true | Selected cause |
Response Body:
Property | Type | Description |
---|---|---|
cause | CauseModel[] | Selected cause |
newTotalDonation | number | The current total donation amount for the selected cause could potentially have a multiplier |
Models
CmsLineItem
export interface ICmsLineItem {
id: any;
price: number;
quantity: number;
discount: number;
}
DonationRecipient
export interface IDonationRecipient {
id: string;
isPortfolio: boolean;
donation: number;
logoUrl: string;
name: string;
description: string;
directDonation: string;
bannerUrl?: string;
city?: string;
state?: string;
streetAddress?: string;
zip?: number;
donationBreakdown?: object; // dictionary
}
CauseModel
export class CauseModel {
isPortfolio: boolean;
id: any;
name: string;
website: string;
logoUrl: string;
streetAddress: string;
city: string;
state: string;
zip: number;
description: string;
multiplier?: number;
categoryId?: number;
categoryName?: string;
categoryLogoUrl?: string;
headline?: string;
bannerUrl?: string;
portfolioCharities?: any[];
default: boolean;
}
ActiveCampaignsModel
export class ActiveCampaignsModel {
onlinePurchase: boolean;
yotpoRedemption: boolean;
roundUpDonation: boolean;
addOnDonation: boolean;
pointOfSale: boolean;
postPurchaseDonation: boolean;
roundUpPos: boolean;
}
CharityResponseModel
export class CharityResponseModel {
id: number;
name: string;
website: string;
logoUrl: string;
streetAddress: string;
city: string;
state: string;
zip: number;
description: string;
categoryId: number;
categoryName: string;
categoryLogoUrl: string;
nteeFullCode: string;
nteeMainCode: number;
nteeSubCode: number;
}
Category Dictionary
Categories = [
{ value: 0, label: 'Art and Culture' },
{ value: 1, label: 'Education' },
{ value: 2, label: 'Environment' },
{ value: 3, label: 'Animal Protection and Services' },
{ value: 4, label: 'Health' },
{ value: 5, label: 'Mental Health and Rehabilitation' },
{ value: 6, label: 'Disease and Disorder' },
{ value: 7, label: 'Medical Research' },
{ value: 8, label: 'Criminal Justice and Legal' },
{ value: 9, label: 'Employment' },
{ value: 10, label: 'Food and Nutrition' },
{ value: 11, label: 'Housing and Shelters' },
{ value: 12, label: 'Public Safety' },
{ value: 13, label: 'Sports' },
{ value: 14, label: 'Youth Development' },
{ value: 15, label: 'Human Services' },
{ value: 16, label: 'International Affairs' },
{ value: 17, label: 'Civil Rights' },
{ value: 18, label: 'Community' },
{ value: 19, label: 'Philanthropy and Volunteering' },
{ value: 20, label: 'Science and Tech' },
{ value: 21, label: 'Social Science' },
{ value: 22, label: 'Public Benefits' },
{ value: 23, label: 'Religion' },
{ value: 24, label: 'Mutual Benefit Organizations' },
{ value: 25, label: 'Other' },
]
Updated about 1 year ago