Skip to content

Commit

Permalink
🪟 🎉 Replace Intercom with Zendesk (#7395)
Browse files Browse the repository at this point in the history
  • Loading branch information
timroes committed Jun 23, 2023
1 parent ee156da commit 1109bd8
Show file tree
Hide file tree
Showing 30 changed files with 119 additions and 135 deletions.
1 change: 0 additions & 1 deletion airbyte-webapp/.env
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
# Environment variables in this file will be passed along to the frontend code, but its content will not be available in the build script
REACT_APP_SEGMENT_TOKEN=6cxNSmQyGSKcATLdJ2pL6WsawkzEMDAN
REACT_APP_INTERCOM_APP_ID=nj1oam7s
REACT_APP_OSANO=16A0CTTE7vE8m1Qif/67beec9b-e563-4736-bdb4-4fe4adc39d48
1 change: 0 additions & 1 deletion airbyte-webapp/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,6 @@
"react-select": "^5.4.0",
"react-slick": "^0.29.0",
"react-use": "^17.4.0",
"react-use-intercom": "^1.5.2",
"react-virtualized-auto-sizer": "^1.0.17",
"react-widgets": "^4.6.1",
"react-window": "^1.8.9",
Expand Down
13 changes: 0 additions & 13 deletions airbyte-webapp/pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

13 changes: 12 additions & 1 deletion airbyte-webapp/scripts/validate-links.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,21 @@ import fetch from "node-fetch";

import { links } from "../src/utils/links";

const IGNORED_LINKS = [
// Cloudflare in front prevents us from checking this without a real browser.
// We assume that the URL won't change really, so it should be fine not validating it.
"supportPortal",
];

async function run() {
// Query all domains and wait for results
const results = await Promise.allSettled(
Object.entries(links).map(([key, url]) => {
if (IGNORED_LINKS.includes(key)) {
console.log(`⚬ [${key}] ${url} ignored for validation`);
return Promise.resolve(true);
}

return fetch(url, { headers: { "user-agent": "ValidateLinksCheck" } })
.then((resp) => {
if (resp.status >= 200 && resp.status < 300) {
Expand All @@ -20,7 +31,7 @@ async function run() {
}
})
.catch((reason) => {
console.error(`X [${key}] ${url} error fetching: ${String(reason)}`);
console.error(`X [${key}] ${url} error fetching: ${JSON.stringify(reason, null, 2)}`);
return Promise.reject({ key, url });
});
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,6 @@

.container {
margin-top: variables.$spacing-md;

&.cloud {
margin-right: (variables.$spacing-intercom - variables.$spacing-xl);
}

transition: opacity variables.$transition-out;

&.hidden {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,6 @@ import { FormattedMessage } from "react-intl";
import { Button } from "components/ui/Button";
import { FlexContainer } from "components/ui/Flex";

import { isCloudApp } from "utils/app";

import styles from "./EditControls.module.scss";
import { ResponseMessage } from "./ResponseMessage";

Expand Down Expand Up @@ -38,7 +36,7 @@ const EditControls: React.FC<EditControlProps> = ({
alignItems="center"
direction="row"
gap="lg"
className={classNames(styles.container, { [styles.cloud]: isCloudApp(), [styles.hidden]: hidden })}
className={classNames(styles.container, { [styles.hidden]: hidden })}
>
<ResponseMessage dirty={dirty} successMessage={successMessage} errorMessage={errorMessage} />
<FlexContainer gap="md">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,3 @@
margin-left: 10px;
min-width: 150px;
}

.chatWithUsBtn {
all: unset;
text-decoration: underline;

&:hover {
cursor: pointer;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import { ConnectionScheduleData, ConnectionScheduleType } from "core/request/Air
import { Action, Namespace } from "core/services/analytics";
import { useAnalyticsService } from "core/services/analytics";
import { useConnectionFormService } from "hooks/services/ConnectionForm/ConnectionFormService";
import { useIntercom } from "packages/cloud/services/thirdParty/intercom";
import { isCloudApp } from "utils/app";
import { links } from "utils/links";

Expand All @@ -30,13 +29,7 @@ const CRON_DEFAULT_VALUE = {
};

const CronErrorChatWithUsButton: React.FC<React.PropsWithChildren<unknown>> = ({ children }) => {
const { show } = useIntercom();

return (
<button type="button" className={styles.chatWithUsBtn} onClick={show}>
{children}
</button>
);
return <ExternalLink href={links.supportPortal}>{children}</ExternalLink>;
};

export const ScheduleField: React.FC = () => {
Expand Down
4 changes: 1 addition & 3 deletions airbyte-webapp/src/config/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,7 @@ export const config: AirbyteWebappConfig = {
authDomain: process.env.REACT_APP_FIREBASE_AUTH_DOMAIN,
authEmulatorHost: process.env.REACT_APP_FIREBASE_AUTH_EMULATOR_HOST,
},
intercom: {
appId: process.env.REACT_APP_INTERCOM_APP_ID,
},
zendeskKey: process.env.REACT_APP_ZENDESK_KEY,
launchDarkly: process.env.REACT_APP_LAUNCHDARKLY_KEY,
datadog: {
applicationId: process.env.REACT_APP_DATADOG_APPLICATION_ID,
Expand Down
4 changes: 1 addition & 3 deletions airbyte-webapp/src/config/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,7 @@ export interface AirbyteWebappConfig {
authDomain?: string;
authEmulatorHost?: string;
};
intercom: {
appId?: string;
};
zendeskKey?: string;
launchDarkly?: string;
datadog: {
applicationId?: string;
Expand Down
3 changes: 0 additions & 3 deletions airbyte-webapp/src/core/api/QueryProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@ import { QueryClient, QueryClientProvider } from "@tanstack/react-query";
import { ReactQueryDevtools } from "@tanstack/react-query-devtools";
import React from "react";

import { isCloudApp } from "utils/app";

const queryClient = new QueryClient({
defaultOptions: {
queries: {
Expand All @@ -20,7 +18,6 @@ export const QueryProvider: React.FC<React.PropsWithChildren<unknown>> = ({ chil
initialIsOpen={false}
position="bottom-right"
toggleButtonProps={{
style: isCloudApp() ? { transform: "translate(-65px, -12px)" } : undefined,
id: "react-query-devtool-btn",
}}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,8 @@ export enum AppActionCodes {
CONNECTOR_DEFINITION_NOT_FOUND = "CONNECTOR_DEFINITION_NOT_FOUND",
CONNECTOR_DOCUMENTATION_FETCH_ERROR = "CONNECTOR_DOCUMENTATION_FETCH_ERROR",
CONNECTOR_DOCUMENTATION_NOT_MARKDOWN = "CONNECTOR_DOCUMENTATION_NOT_MARKDOWN",
/**
* Zendesk chat was tried to open while Zendesk didn't load properly.
*/
ZENDESK_OPEN_FAILURE = "ZENDESK_OPEN_FAILURE",
}
6 changes: 3 additions & 3 deletions airbyte-webapp/src/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,9 @@
"sidebar.documentation": "Documentation",
"sidebar.joinSlack": "Join our Slack",
"sidebar.status": "Airbyte Status",
"sidebar.chat": "Chat with us",
"sidebar.inAppHelpCenter": "In-App Support",
"sidebar.support": "Support",
"sidebar.supportTicket": "Submit a Ticket",
"sidebar.supportPortal": "Support Portal",
"sidebar.recipes": "Tutorials - Use cases",
"sidebar.builder": "Builder",
"sidebar.upcomingFeatures": "Upcoming features",
Expand Down Expand Up @@ -544,7 +544,7 @@
"form.cronExpression": "Cron expression",
"form.cronExpression.placeholder": "Cron expression",
"form.cronExpression.error": "Invalid cron expression",
"form.cronExpression.underOneHourNotAllowed": "Interested in syncing more frequently than once an hour? <lnk>Chat with us</lnk> to unlock this feature.",
"form.cronExpression.underOneHourNotAllowed": "Interested in syncing more frequently than once an hour? <lnk>Contact us</lnk> to unlock this feature.",
"form.cronExpression.message": "Enter a <lnk>cron expression</lnk> for when syncs should run (ex. \"0 0 12 * * ?\" => Will sync at 12:00 PM every day)",
"form.frequency.placeholder": "Select a frequency",
"form.frequency.message": "Set how often data should sync to the destination",
Expand Down
4 changes: 2 additions & 2 deletions airbyte-webapp/src/packages/cloud/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import { theme } from "packages/cloud/theme";
import { ConnectorBuilderTestInputProvider } from "services/connectorBuilder/ConnectorBuilderTestInputService";

import { AppServicesProvider } from "./services/AppServicesProvider";
import { IntercomProvider } from "./services/thirdParty/intercom/IntercomProvider";
import { ZendeskProvider } from "./services/thirdParty/zendesk";

const messages = { ...en, ...cloudLocales };

Expand All @@ -45,7 +45,7 @@ const Services: React.FC<React.PropsWithChildren<unknown>> = ({ children }) => (
<AuthenticationProvider>
<ConnectorBuilderTestInputProvider>
<HelmetProvider>
<IntercomProvider>{children}</IntercomProvider>
<ZendeskProvider>{children}</ZendeskProvider>
</HelmetProvider>
</ConnectorBuilderTestInputProvider>
</AuthenticationProvider>
Expand Down

This file was deleted.

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import { useEffect } from "react";
import { useEffectOnce } from "react-use";

import { config } from "config";
import { useCurrentWorkspaceId } from "services/workspaces/WorkspacesService";

import { useAuthService } from "../../auth/AuthService";

import "./zendesk.module.scss";

declare global {
interface Window {
zE?: (type: string, action: string, params?: unknown) => void;
zESettings?: unknown;
}
}

export const ZendeskProvider: React.FC<React.PropsWithChildren<unknown>> = ({ children }) => {
const { zendeskKey } = config;
const { user } = useAuthService();
const workspaceId = useCurrentWorkspaceId();

useEffectOnce(() => {
if (zendeskKey) {
const script = document.createElement("script");
script.id = "ze-snippet";
script.src = `https://static.zdassets.com/ekr/snippet.js?key=${zendeskKey}`;
document.body.appendChild(script);
}
});

useEffect(() => {
window.zE?.("webWidget", "prefill", {
name: { value: user?.name },
email: { value: user?.email },
});
}, [user]);

useEffect(() => {
window.zESettings = {
webWidget: {
contactForm: {
// Only allow Cloud ticket form
ticketForms: [{ id: "16332000182427" }],
fields: [{ id: "16334185233691", prefill: { "*": `https://cloud.airbyte.com/workspaces/${workspaceId}` } }],
},
},
};
}, [workspaceId]);

return <>{children}</>;
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export { ZendeskProvider } from "./ZendeskProvider";
export { useZendesk } from "./useZendesk";
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import { useCallback, useMemo } from "react";

import { AppActionCodes, useAppMonitoringService } from "hooks/services/AppMonitoringService";

export const useZendesk = () => {
const { trackAction } = useAppMonitoringService();

const openZendesk = useCallback(() => {
if (window.zE) {
window.zE("webWidget", "open");
} else {
trackAction(AppActionCodes.ZENDESK_OPEN_FAILURE);
}
}, [trackAction]);

return useMemo(() => ({ openZendesk }), [openZendesk]);
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
:global(iframe#launcher) {
// Hide the launcher icon. Unfortunately there is no setting in the API for this
display: none;
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ import { CloudRoutes } from "packages/cloud/cloudRoutePaths";
import { useExperimentSpeedyConnection } from "packages/cloud/components/experiments/SpeedyConnection/hooks/useExperimentSpeedyConnection";
import { SpeedyConnectionBanner } from "packages/cloud/components/experiments/SpeedyConnection/SpeedyConnectionBanner";
import { useAuthService } from "packages/cloud/services/auth/AuthService";
import { useIntercom } from "packages/cloud/services/thirdParty/intercom";
import { RoutePaths } from "pages/routePaths";
import { useCurrentWorkspace } from "services/workspaces/WorkspacesService";
import { ResourceNotFoundErrorBoundary } from "views/common/ResourceNotFoundErrorBoundary";
Expand All @@ -36,7 +35,6 @@ import { LOW_BALANCE_CREDIT_THRESHOLD } from "../../billing/BillingPage/componen
import { WorkspacePopout } from "../../workspaces/WorkspacePopout";

const CloudMainView: React.FC<React.PropsWithChildren<unknown>> = (props) => {
useIntercom();
const workspace = useCurrentWorkspace();
const cloudWorkspace = useGetCloudWorkspace(workspace.workspaceId);
const isShowAdminWarningEnabled = useFeature(FeatureItem.ShowAdminWarningInWorkspace);
Expand Down
Loading

0 comments on commit 1109bd8

Please sign in to comment.