Skip to content
Draft
Show file tree
Hide file tree
Changes from all 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
83 changes: 68 additions & 15 deletions assets/src/components/Dashboard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import {Box, Flex} from 'theme-ui';
import {ChatWidget, Papercups} from '@papercups-io/chat-widget';
// import {Storytime} from '../lib/storytime'; // For testing
import {Storytime} from '@papercups-io/storytime';
import {colors, Layout, Menu, Sider} from './common';
import {colors, Menu, Sider, Text} from './common';
import {
ApiOutlined,
CodeOutlined,
Expand Down Expand Up @@ -42,7 +42,7 @@ import {
hasValidStripeKey,
isWindowHidden,
} from '../utils';
import {Account, User} from '../types';
import {Account, AccountFeatures, User} from '../types';
import {useAuth} from './auth/AuthProvider';
import {SocketProvider, SocketContext} from './auth/SocketProvider';
import AccountOverview from './settings/AccountOverview';
Expand Down Expand Up @@ -100,10 +100,6 @@ const {

const TITLE_FLASH_INTERVAL = 2000;

const shouldDisplayChat = (pathname: string) => {
return isHostedProd && pathname !== '/settings/chat-widget';
};

const getSectionKey = (pathname: string) => {
if (pathname.startsWith('/companies')) {
return ['customers', 'companies'];
Expand Down Expand Up @@ -195,6 +191,42 @@ const ChatWithUs = ({
);
};

const TRIAL_BANNER_HEIGHT = 32;

const TrialBanner = ({days}: {days: number}) => {
return (
<Flex
sx={{
position: 'fixed',
zIndex: 99999,
top: 0,
left: 0,
right: 0,
height: TRIAL_BANNER_HEIGHT,
letterSpacing: 0.2,
justifyContent: 'center',
alignItems: 'center',
bg: colors.note,
color: colors.white,
}}
>
{days > 0 ? (
<Text strong>
Your trial will expire in {days} days. Go to the{' '}
<Link to="/settings/billing">billing page</Link> to manage your
subscription.
</Text>
) : (
<Text strong>
Your free trial has expired. Go to the{' '}
<Link to="/settings/billing">billing page</Link> to manage your
subscription.
</Text>
)}
</Flex>
);
};

// TODO: not sure if this is the best way to handle this, but the goal
// of this component is to flash the number of unread messages in the
// tab (i.e. HTML title) so users can see when new messages arrive
Expand Down Expand Up @@ -249,6 +281,12 @@ const Dashboard = (props: RouteComponentProps) => {

const [section, key] = getSectionKey(pathname);
const totalNumUnread = unread.conversations.open || 0;

const features = account?.features || ({} as AccountFeatures);
const shouldDisplayChat =
isHostedProd &&
pathname !== '/settings/chat-widget' &&
features.can_contact_support;
const shouldDisplayBilling = hasValidStripeKey();
const shouldHighlightInbox =
totalNumUnread > 0 && section !== 'conversations';
Expand Down Expand Up @@ -281,17 +319,29 @@ const Dashboard = (props: RouteComponentProps) => {
}, [currentUser]);

return (
<Layout>
<Flex
sx={{
position: 'relative',
flex: 'auto',
flexDirection: 'column',
minHeight: 0,
marginTop: TRIAL_BANNER_HEIGHT,
}}
>
<DashboardHtmlHead totalNumUnread={totalNumUnread} />

<TrialBanner days={14} />

<Sider
width={DASHBOARD_COLLAPSED_SIDER_WIDTH}
collapsed={true}
style={{
overflow: 'auto',
height: '100vh',
position: 'fixed',
height: '100%',
position: 'absolute',

left: 0,
bottom: 0,
color: colors.white,
}}
>
Expand Down Expand Up @@ -438,7 +488,7 @@ const Dashboard = (props: RouteComponentProps) => {

<Box py={3}>
<Menu mode="inline" theme="dark" selectable={false}>
{shouldDisplayChat(pathname) && (
{shouldDisplayChat && (
<Menu.Item
title="Chat with us!"
icon={<SmileOutlined />}
Expand All @@ -461,8 +511,11 @@ const Dashboard = (props: RouteComponentProps) => {
</Flex>
</Sider>

<Layout
style={{
<Flex
sx={{
flex: 'auto',
flexDirection: 'column',
minHeight: 0,
marginLeft: DASHBOARD_COLLAPSED_SIDER_WIDTH,
background: colors.white,
}}
Expand Down Expand Up @@ -580,12 +633,12 @@ const Dashboard = (props: RouteComponentProps) => {
<Route path="/inboxes*" component={InboxesDashboard} />
<Route path="*" render={() => <Redirect to="/conversations/all" />} />
</Switch>
</Layout>
</Flex>

{currentUser && shouldDisplayChat(pathname) && (
{currentUser && shouldDisplayChat && (
<ChatWithUs currentUser={currentUser} account={account} />
)}
</Layout>
</Flex>
);
};

Expand Down
3 changes: 2 additions & 1 deletion assets/src/components/auth/AuthProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import React, {useContext} from 'react';
import {getAuthTokens, setAuthTokens, removeAuthTokens} from '../../storage';
import * as API from '../../api';
import logger from '../../logger';
import {inspect} from '../../utils';
import {Account, User} from '../../types';

export const AuthContext = React.createContext<{
Expand Down Expand Up @@ -115,7 +116,7 @@ export class AuthProvider extends React.Component<Props, State> {

fetchCurrentAccount = async () => {
return API.fetchAccountInfo()
.then((account) => account)
.then((account) => inspect(account))
.catch((err) => {
logger.error('Could not retrieve current account:', err);

Expand Down
20 changes: 16 additions & 4 deletions assets/src/components/conversations/ConversationsDashboard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -540,15 +540,27 @@ export const ConversationsDashboard = ({
}

return (
<Layout style={{background: colors.white}}>
<Flex
sx={{
position: 'relative',
flex: 'auto',
flexDirection: 'column',
minHeight: 0,
background: colors.white,
}}
>
<Sider
theme="light"
width={CONVERSATIONS_DASHBOARD_SIDER_WIDTH}
style={{
borderRight: '1px solid #f0f0f0',

overflow: 'auto',
height: '100vh',
position: 'fixed',
height: '100%',
position: 'absolute',

left: 0,
bottom: 0,
}}
>
<Box sx={{position: 'relative', borderBottom: '1px solid #f0f0f0'}}>
Expand Down Expand Up @@ -634,7 +646,7 @@ export const ConversationsDashboard = ({
/>
)}
</Layout>
</Layout>
</Flex>
);
};

Expand Down
32 changes: 23 additions & 9 deletions assets/src/components/inboxes/InboxesDashboard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import {
import {Box, Flex} from 'theme-ui';
import {MenuItemProps} from 'antd/lib/menu/MenuItem';

import {colors, Badge, Layout, Menu, Sider} from '../common';
import {colors, Badge, Menu, Sider} from '../common';
import {PlusOutlined, SettingOutlined} from '../icons';
import {INBOXES_DASHBOARD_SIDER_WIDTH} from '../../utils';
import * as API from '../../api';
Expand Down Expand Up @@ -93,14 +93,25 @@ const InboxesDashboard = (props: RouteComponentProps) => {
};

return (
<Layout style={{background: colors.white}}>
<Flex
sx={{
position: 'relative',
flex: 'auto',
flexDirection: 'column',
minHeight: 0,
background: colors.white,
}}
>
<Sider
className="Dashboard-Sider"
width={INBOXES_DASHBOARD_SIDER_WIDTH}
style={{
overflow: 'auto',
height: '100vh',
position: 'fixed',
height: '100%',
position: 'absolute',

left: 0,
bottom: 0,
color: colors.white,
}}
>
Expand Down Expand Up @@ -265,10 +276,13 @@ const InboxesDashboard = (props: RouteComponentProps) => {
</Flex>
</Sider>

<Layout
style={{
background: colors.white,
<Flex
sx={{
flex: 'auto',
flexDirection: 'column',
minHeight: 0,
marginLeft: INBOXES_DASHBOARD_SIDER_WIDTH,
background: colors.white,
}}
>
<Switch>
Expand Down Expand Up @@ -332,8 +346,8 @@ const InboxesDashboard = (props: RouteComponentProps) => {
<Route path="/inboxes" component={InboxesOverview} />
<Route path="*" render={() => <Redirect to="/conversations/all" />} />
</Switch>
</Layout>
</Layout>
</Flex>
</Flex>
);
};

Expand Down
18 changes: 18 additions & 0 deletions assets/src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,24 @@ export type Account = {
widget_settings: Array<WidgetSettings>;
working_hours: Array<any>;
settings?: AccountSettings | null;
features?: AccountFeatures;
};

export type AccountFeatures = {
effective_subscription_plan?: string;
has_valid_subscription?: boolean;
can_reply_via_slack?: boolean;
can_reply_via_dashboard?: boolean;
can_use_private_notes?: boolean;
can_use_webhooks?: boolean;
can_use_lambdas?: boolean;
can_contact_support?: boolean;
can_add_inboxes?: boolean;
can_use_storytime?: boolean;
is_in_free_trial?: boolean;
is_early_adopter?: boolean;
days_left_in_trial?: number;
max_account_users?: number;
};

export type AccountSettings = {
Expand Down
6 changes: 6 additions & 0 deletions assets/src/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,12 @@ export const sleep = (ms: number) => new Promise((res) => setTimeout(res, ms));

export const noop = () => {};

export const inspect = (data: any) => {
console.debug('[Inspect]', data);

return data;
};

export const hasValidStripeKey = () => {
const key = REACT_APP_STRIPE_PUBLIC_KEY;

Expand Down
Loading