diff --git a/README.md b/README.md
index 2718f51c..90ff2f09 100644
--- a/README.md
+++ b/README.md
@@ -50,6 +50,7 @@ const HomePage = () => {
## API
* [IntercomProvider](#intercomprovider)
* [useIntercom](#useintercom)
+* [IntercomProps](#intercomprops)
### IntercomProvider
`IntercomProvider` is used to initialize the `window.Intercom` instance. It makes sure the initialization is only done once. If any listeners are passed, the `IntercomProvider` will make sure these are attached.
@@ -177,6 +178,24 @@ const HomePage = () => {
);
};
```
+### IntercomProps
+All the Intercom default attributes/props are camel cased (`appId` instead of `app_id`) in `react-use-intercom`, see [IntercomProps](src/types.ts) to see what attributes you can pass to `boot` or `update`. Or check the Intercom [docs](https://developers.intercom.com/installing-intercom/docs/javascript-api-attributes-objects)
+ to see all the available attributes/props.
+
+ **Remark** - all the listed Intercom attributes [here](https://developers.intercom.com/installing-intercom/docs/javascript-api-attributes-objects) are snake cased, in `react-use-intercom` are these camel cased.
+
+ #### Custom attributes
+ Still want to pass custom attributes to Intercom? Whether `boot` or `update` is used, you can add your custom properties by passing these through `customAttributes` in the `boot` or `update` method.
+
+**Remark** - the keys of the `customAttributes` object should be snake cased. They are rawly passed to Intercom.
+ ```javascript
+ const { boot } = useIntercom();
+
+ boot({
+ name: 'Russo',
+ customAttributes: { custom_attribute_key: 'hi there' },
+})
+ ```
## Playground
Example playground to showcase the functionalities of `react-use-intercom`.
diff --git a/cypress/integration/mappers.ts b/cypress/integration/mappers.ts
new file mode 100644
index 00000000..f56fb650
--- /dev/null
+++ b/cypress/integration/mappers.ts
@@ -0,0 +1,89 @@
+///
+
+describe('mappers', () => {
+ // TODO: 'contain' does not work for objects (like avatar...)
+ it('should map passed props to raw propped on `boot`', () => {
+ cy.visit('/useIntercom');
+
+ cy.window().should('not.have.property', 'intercomSettings');
+
+ cy.get('[data-cy=boot-extended-seeded]').click();
+
+ cy.window().should('have.property', 'Intercom');
+
+ cy.window()
+ .its('intercomSettings')
+ .should('be.an', 'object')
+ .and('contain', {
+ app_id: 'jcabc7e3',
+ name: 'Russo',
+ action_color: 'red',
+ utm_content: 'content',
+ vertical_padding: 10,
+ alignment: 'left',
+ background_color: 'green',
+ created_at: 'now',
+ custom_launcher_selector: '.id',
+ hide_default_launcher: false,
+ horizontal_padding: 10,
+ language_override: 'en',
+ phone: '0470',
+ session_duration: 1000,
+ unsubscribed_from_emails: false,
+ last_request_at: 'now',
+ utm_campaign: 'campaign',
+ utm_source: 'source',
+ utm_medium: 'medium',
+ utm_term: 'term',
+ user_id: '12345',
+ my_custom_attribute: 'custom_attribute_value',
+ my_second_custom_attribute: 'second_custom_attribute_value',
+ })
+ .and('not.contain', {
+ my_fifth_custom_attribute: 'custom_attribute_value',
+ });
+
+ cy.window()
+ .its('intercomSettings')
+ .its('avatar')
+ .should('be.an', 'object')
+ .and('deep.equal', {
+ type: 'image',
+ image_url: 'https://github.com/devrnt/react-use-intercom',
+ });
+
+ cy.window()
+ .its('intercomSettings')
+ .its('company')
+ .should('be.an', 'object')
+ .and('deep.equal', {
+ company_id: 'company',
+ created_at: 'now',
+ industry: 'industry',
+ monthly_spend: 10,
+ name: 'name',
+ plan: 'plan',
+ size: 12,
+ user_count: 100,
+ website: 'https://github.com/devrnt/react-use-intercom',
+ });
+
+ cy.window()
+ .its('intercomSettings')
+ .its('companies')
+ .should('be.an', 'array')
+ .and('deep.equal', [
+ {
+ company_id: 'company',
+ created_at: 'now',
+ industry: 'industry',
+ monthly_spend: 10,
+ name: 'name',
+ plan: 'plan',
+ size: 12,
+ user_count: 100,
+ website: 'https://github.com/devrnt/react-use-intercom',
+ },
+ ]);
+ });
+});
diff --git a/cypress/integration/visitorId.ts b/cypress/integration/visitorId.ts
index 2369a994..aefdd8f0 100644
--- a/cypress/integration/visitorId.ts
+++ b/cypress/integration/visitorId.ts
@@ -7,7 +7,7 @@ describe('getVisitorId', () => {
cy.get('[data-cy=boot]').click();
cy.get('[data-cy="visitorIdValue"]').should('not.be.visible');
- cy.wait(1500);
+ cy.wait(2000);
cy.get('[data-cy="visitorId"]').click();
cy.get('[data-cy="visitorIdValue"]').should('be.visible');
diff --git a/example/modules/useIntercom/useIntercom.tsx b/example/modules/useIntercom/useIntercom.tsx
index df414fc4..5d1e574f 100644
--- a/example/modules/useIntercom/useIntercom.tsx
+++ b/example/modules/useIntercom/useIntercom.tsx
@@ -34,13 +34,80 @@ const RawUseIntercomPage = () => {
showMessages,
showNewMessages,
getVisitorId,
- startTour,
trackEvent,
} = useIntercom();
+ const handleBoot = React.useCallback(() => boot(), [boot]);
- const handleBoot = React.useCallback(() => boot({ name: 'Russo' }), [boot]);
+ const handleSeededBoot = React.useCallback(() => boot({ name: 'Russo' }), [
+ boot,
+ ]);
+
+ const handleExtendedSeededBoot = React.useCallback(
+ () =>
+ boot({
+ name: 'Russo',
+ actionColor: 'red',
+ email: 'russo@email.com',
+ utmContent: 'content',
+ verticalPadding: 10,
+ alignment: 'left',
+ avatar: {
+ type: 'image',
+ imageUrl: 'https://github.com/devrnt/react-use-intercom',
+ },
+ company: {
+ companyId: 'company',
+ createdAt: 'now',
+ industry: 'industry',
+ monthlySpend: 10,
+ name: 'name',
+ plan: 'plan',
+ size: 12,
+ userCount: 100,
+ website: 'https://github.com/devrnt/react-use-intercom',
+ },
+ companies: [
+ {
+ companyId: 'company',
+ createdAt: 'now',
+ industry: 'industry',
+ monthlySpend: 10,
+ name: 'name',
+ plan: 'plan',
+ size: 12,
+ userCount: 100,
+ website: 'https://github.com/devrnt/react-use-intercom',
+ },
+ ],
+ backgroundColor: 'green',
+ createdAt: 'now',
+ customLauncherSelector: '.id',
+ hideDefaultLauncher: false,
+ horizontalPadding: 10,
+ languageOverride: 'en',
+ phone: '0470',
+ sessionDuration: 1000,
+ unsubscribedFromEmails: false,
+ userHash: '123',
+ lastRequestAt: 'now',
+ utmCampaign: 'campaign',
+ utmSource: 'source',
+ utmMedium: 'medium',
+ utmTerm: 'term',
+ userId: '12345',
+ customAttributes: {
+ my_custom_attribute: 'custom_attribute_value',
+ my_second_custom_attribute: 'second_custom_attribute_value',
+ },
+ }),
+ [boot],
+ );
const handleUpdate = React.useCallback(() => {
+ update();
+ }, [update]);
+
+ const handleSeededUpdate = React.useCallback(() => {
update({ name: 'ponas' });
}, [update]);
@@ -75,13 +142,27 @@ const RawUseIntercomPage = () => {
boots the Intercom instance, not needed if autoBoot in{' '}
IntercomProvider is true
-
+
-
boots the Intercom instance with given props
-
+
+
+ -
+
+ boots the Intercom instance with given extended props
+
+
-
shuts down the Intercom instance
@@ -101,7 +182,7 @@ const RawUseIntercomPage = () => {
-
Initiates a 'ping'
-
+
-
@@ -110,7 +191,7 @@ const RawUseIntercomPage = () => {
-
diff --git a/src/mappers.ts b/src/mappers.ts
index 5767cb93..bbd85a2d 100644
--- a/src/mappers.ts
+++ b/src/mappers.ts
@@ -134,8 +134,9 @@ export const mapDataAttributesToRawDataAttributes = (
unsubscribed_from_emails: attributes.unsubscribedFromEmails,
language_override: attributes.languageOverride,
utm_campaign: attributes.utmCampaign,
+ utm_content: attributes.utmContent,
utm_medium: attributes.utmMedium,
- utm_source: attributes.utm_source,
+ utm_source: attributes.utmSource,
utm_term: attributes.utmTerm,
avatar:
attributes.avatar &&
@@ -143,10 +144,11 @@ export const mapDataAttributesToRawDataAttributes = (
user_hash: attributes.userHash,
company:
attributes.company &&
- mapDataAttributesCompanyToRawDataAttributesCompany(attributes.c),
+ mapDataAttributesCompanyToRawDataAttributesCompany(attributes.company),
companies: attributes.companies?.map(
mapDataAttributesCompanyToRawDataAttributesCompany,
),
+ ...attributes.customAttributes,
});
export const mapRawIntercomPropsToIntercomProps = (
diff --git a/src/types.ts b/src/types.ts
index 5ff0ee34..12260df0 100644
--- a/src/types.ts
+++ b/src/types.ts
@@ -127,7 +127,7 @@ export type RawDataAttributes = {
user_hash?: string;
company?: RawDataAttributesCompany;
companies?: RawDataAttributesCompany[];
- [custom_property: string]: any;
+ customAttributes?: Record;
};
export type DataAttributes = {
@@ -210,11 +210,19 @@ export type DataAttributes = {
companies?: DataAttributesCompany[];
/**
* You can do this anytime by adding additional key/value pairs to your intercomSettings code snippet
+ * These should be raw snake_cased
+ *
+ * @example
+ * ```
+ * customAttributes={
+ * my_custom_attibute: 'my attribute value'
+ * }
+ * ```
*
* @see {@link https://www.intercom.com/help/en/articles/179-send-custom-user-attributes-to-intercom}
* @remarks The key is the attribute name. The value is a placeholder for the data you’ll track
*/
- [customProperty: string]: any;
+ customAttributes?: Record;
};
export type IntercomMethod =