Skip to content

Commit f78935f

Browse files
committed
Make hook for preferred proxy
1 parent b2e3efb commit f78935f

File tree

12 files changed

+171
-67
lines changed

12 files changed

+171
-67
lines changed

site/src/components/AppLink/AppLink.tsx

Lines changed: 19 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import * as TypesGen from "../../api/typesGenerated"
1010
import { generateRandomString } from "../../utils/random"
1111
import { BaseIcon } from "./BaseIcon"
1212
import { ShareIcon } from "./ShareIcon"
13+
import { usePreferredProxy } from "hooks/usePreferredProxy"
1314

1415
const Language = {
1516
appTitle: (appName: string, identifier: string): string =>
@@ -29,6 +30,11 @@ export const AppLink: FC<AppLinkProps> = ({
2930
workspace,
3031
agent,
3132
}) => {
33+
const preferredProxy = usePreferredProxy()
34+
const preferredPathBase = preferredProxy ? preferredProxy.path_app_url : ""
35+
// Use the proxy host subdomain if it's configured.
36+
appsHost = preferredProxy ? preferredProxy.wildcard_hostname : appsHost
37+
3238
const styles = useStyles()
3339
const username = workspace.owner_name
3440

@@ -43,14 +49,14 @@ export const AppLink: FC<AppLinkProps> = ({
4349

4450
// The backend redirects if the trailing slash isn't included, so we add it
4551
// here to avoid extra roundtrips.
46-
let href = `/@${username}/${workspace.name}.${
47-
agent.name
48-
}/apps/${encodeURIComponent(appSlug)}/`
52+
let href = `${preferredPathBase}/@${username}/${workspace.name}.${agent.name
53+
}/apps/${encodeURIComponent(appSlug)}/`
4954
if (app.command) {
50-
href = `/@${username}/${workspace.name}.${
51-
agent.name
52-
}/terminal?command=${encodeURIComponent(app.command)}`
55+
href = `${preferredPathBase}/@${username}/${workspace.name}.${agent.name
56+
}/terminal?command=${encodeURIComponent(app.command)}`
5357
}
58+
59+
// TODO: @emyrk handle proxy subdomains.
5460
if (appsHost && app.subdomain) {
5561
const subdomain = `${appSlug}--${agent.name}--${workspace.name}--${username}`
5662
href = `${window.location.protocol}//${appsHost}/`.replace("*", subdomain)
@@ -104,13 +110,13 @@ export const AppLink: FC<AppLinkProps> = ({
104110
onClick={
105111
canClick
106112
? (event) => {
107-
event.preventDefault()
108-
window.open(
109-
href,
110-
Language.appTitle(appDisplayName, generateRandomString(12)),
111-
"width=900,height=600",
112-
)
113-
}
113+
event.preventDefault()
114+
window.open(
115+
href,
116+
Language.appTitle(appDisplayName, generateRandomString(12)),
117+
"width=900,height=600",
118+
)
119+
}
114120
: undefined
115121
}
116122
>

site/src/components/DeploySettingsLayout/Badges.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ export const NotHealthyBadge: FC = () => {
3535
const styles = useStyles()
3636
return (
3737
<span className={combineClasses([styles.badge, styles.errorBadge])}>
38-
Error
38+
Unhealthy
3939
</span>
4040
)
4141
}

site/src/components/PortForwardButton/PortForwardButton.tsx

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -35,18 +35,20 @@ export const portForwardURL = (
3535
): string => {
3636
const { location } = window
3737

38-
const subdomain = `${
39-
isNaN(port) ? 3000 : port
40-
}--${agentName}--${workspaceName}--${username}`
38+
const subdomain = `${isNaN(port) ? 3000 : port
39+
}--${agentName}--${workspaceName}--${username}`
4140
return `${location.protocol}//${host}`.replace("*", subdomain)
4241
}
4342

4443
const TooltipView: React.FC<PortForwardButtonProps> = (props) => {
4544
const { host, workspaceName, agentName, agentId, username } = props
45+
const preferredProxy = usePreferredProxy()
46+
const portHost = preferredProxy ? preferredProxy.wildcard_hostname : host
47+
4648
const styles = useStyles()
4749
const [port, setPort] = useState("3000")
4850
const urlExample = portForwardURL(
49-
host,
51+
portHost,
5052
parseInt(port),
5153
agentName,
5254
workspaceName,
@@ -104,7 +106,7 @@ const TooltipView: React.FC<PortForwardButtonProps> = (props) => {
104106
{ports &&
105107
ports.map((p, i) => {
106108
const url = portForwardURL(
107-
host,
109+
portHost,
108110
p.port,
109111
agentName,
110112
workspaceName,

site/src/components/SettingsLayout/Sidebar.tsx

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import { combineClasses } from "utils/combineClasses"
1010
import AccountIcon from "@material-ui/icons/Person"
1111
import SecurityIcon from "@material-ui/icons/LockOutlined"
1212
import PublicIcon from '@material-ui/icons/Public';
13+
import { useDashboard } from "components/Dashboard/DashboardProvider"
1314

1415
const SidebarNavItem: FC<
1516
PropsWithChildren<{ href: string; icon: ReactNode }>
@@ -42,6 +43,7 @@ const SidebarNavItemIcon: React.FC<{ icon: ElementType }> = ({
4243

4344
export const Sidebar: React.FC<{ user: User }> = ({ user }) => {
4445
const styles = useStyles()
46+
const dashboard = useDashboard()
4547

4648
return (
4749
<nav className={styles.sidebar}>
@@ -77,13 +79,14 @@ export const Sidebar: React.FC<{ user: User }> = ({ user }) => {
7779
>
7880
Tokens
7981
</SidebarNavItem>
80-
{/* TODO: @emyrk this should only be shown if the 'moons' experiment is enabled */}
81-
<SidebarNavItem
82-
href="workspace-proxies"
83-
icon={<SidebarNavItemIcon icon={PublicIcon} />}
84-
>
85-
Workspace Proxy
86-
</SidebarNavItem>
82+
{
83+
dashboard.experiments.includes("moons") && <SidebarNavItem
84+
href="workspace-proxies"
85+
icon={<SidebarNavItemIcon icon={PublicIcon} />}
86+
>
87+
Workspace Proxy
88+
</SidebarNavItem>
89+
}
8790
</nav>
8891
)
8992
}

site/src/components/TerminalLink/TerminalLink.tsx

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import { SecondaryAgentButton } from "components/Resources/AgentButton"
33
import { FC } from "react"
44
import * as TypesGen from "../../api/typesGenerated"
55
import { generateRandomString } from "../../utils/random"
6+
import { usePreferredProxy } from "hooks/usePreferredProxy"
67

78
export const Language = {
89
linkText: "Terminal",
@@ -27,9 +28,11 @@ export const TerminalLink: FC<React.PropsWithChildren<TerminalLinkProps>> = ({
2728
userName = "me",
2829
workspaceName,
2930
}) => {
30-
const href = `/@${userName}/${workspaceName}${
31-
agentName ? `.${agentName}` : ""
32-
}/terminal`
31+
const preferredProxy = usePreferredProxy()
32+
const preferredPathBase = preferredProxy ? preferredProxy.path_app_url : ""
33+
34+
const href = `${preferredPathBase}/@${userName}/${workspaceName}${agentName ? `.${agentName}` : ""
35+
}/terminal`
3336

3437
return (
3538
<Link

site/src/hooks/usePreferredProxy.ts

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import { Region } from "api/typesGenerated"
2+
import { useDashboard } from "components/Dashboard/DashboardProvider"
3+
4+
export const usePreferredProxy = (): Region | undefined => {
5+
const dashboard = useDashboard()
6+
// Only use preferred proxy if the user has the moons experiment enabled
7+
if(!dashboard?.experiments.includes("moons")) {
8+
return undefined
9+
}
10+
11+
const str = localStorage.getItem("preferred-proxy")
12+
if (str === undefined || str === null) {
13+
return undefined
14+
}
15+
const proxy = JSON.parse(str)
16+
if (proxy.id === undefined || proxy.id === null) {
17+
return undefined
18+
}
19+
return proxy
20+
}

site/src/i18n/en/proxyPage.json

Lines changed: 0 additions & 19 deletions
This file was deleted.

site/src/pages/UserSettingsPage/WorkspaceProxyPage/WorkspaceProxyPage.tsx

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { FC, PropsWithChildren, useState } from "react"
22
import { Section } from "components/SettingsLayout/Section"
33
import { WorkspaceProxyPageView } from "./WorkspaceProxyView"
44
import makeStyles from "@material-ui/core/styles/makeStyles"
5-
import { useTranslation, Trans } from "react-i18next"
5+
import { Trans } from "react-i18next"
66
import { useWorkspaceProxiesData } from "./hooks"
77
import { Region } from "api/typesGenerated"
88
import { displayError } from "components/GlobalSnackbar/utils"
@@ -15,10 +15,9 @@ import { displayError } from "components/GlobalSnackbar/utils"
1515

1616
export const WorkspaceProxyPage: FC<PropsWithChildren<unknown>> = () => {
1717
const styles = useStyles()
18-
const { t } = useTranslation("proxyPage")
1918

2019
const description = (
21-
<Trans t={t} i18nKey="description" values={{}}>
20+
<Trans values={{}}>
2221
Workspace proxies are used to reduce the latency of connections to a workspace.
2322
To get the best experience, choose the workspace proxy that is closest located to
2423
you.
@@ -37,7 +36,7 @@ export const WorkspaceProxyPage: FC<PropsWithChildren<unknown>> = () => {
3736
return (
3837
<>
3938
<Section
40-
title={t("title")}
39+
title="Workspace Proxies"
4140
className={styles.section}
4241
description={description}
4342
layout="fluid"
@@ -53,8 +52,15 @@ export const WorkspaceProxyPage: FC<PropsWithChildren<unknown>> = () => {
5352
displayError("Please select a healthy workspace proxy.")
5453
return
5554
}
56-
savePreferredProxy(proxy)
57-
setPreffered(proxy)
55+
// normProxy is a normalized proxy to
56+
const normProxy = {
57+
...proxy,
58+
// Trim trailing slashes to be consistent
59+
path_app_url: proxy.path_app_url.replace(/\/$/, ''),
60+
}
61+
62+
savePreferredProxy(normProxy)
63+
setPreffered(normProxy)
5864
}}
5965
/>
6066
</Section>
@@ -72,9 +78,6 @@ const useStyles = makeStyles((theme) => ({
7278
borderRadius: 2,
7379
},
7480
},
75-
tokenActions: {
76-
marginBottom: theme.spacing(1),
77-
},
7881
}))
7982

8083
export default WorkspaceProxyPage

site/src/pages/UserSettingsPage/WorkspaceProxyPage/WorkspaceProxyRow.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ const ProxyStatus: FC<{
6767

6868
const useStyles = makeStyles((theme) => ({
6969
preferredrow: {
70-
// TODO: What color should I put here?
70+
// TODO: What is the best way to show what proxy is currently being used?
7171
backgroundColor: theme.palette.secondary.main,
7272
outline: `3px solid ${theme.palette.secondary.light}`,
7373
outlineOffset: -3,

site/src/pages/UserSettingsPage/WorkspaceProxyPage/WorkspaceProxyView.tsx

Lines changed: 5 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import { useTheme } from "@material-ui/core/styles"
21
import Table from "@material-ui/core/Table"
32
import TableBody from "@material-ui/core/TableBody"
43
import TableCell from "@material-ui/core/TableCell"
@@ -11,7 +10,6 @@ import { TableEmpty } from "components/TableEmpty/TableEmpty"
1110
import { TableLoader } from "components/TableLoader/TableLoader"
1211
import { FC } from "react"
1312
import { AlertBanner } from "components/AlertBanner/AlertBanner"
14-
import { useTranslation } from "react-i18next"
1513
import { Region } from "api/typesGenerated"
1614
import { ProxyRow } from "./WorkspaceProxyRow"
1715

@@ -38,8 +36,6 @@ export const WorkspaceProxyPageView: FC<
3836
selectProxyError,
3937
preferredProxy,
4038
}) => {
41-
const { t } = useTranslation("proxyPage")
42-
4339
return (
4440
<Stack>
4541
{Boolean(getWorkspaceProxiesError) && (
@@ -52,9 +48,9 @@ export const WorkspaceProxyPageView: FC<
5248
<Table>
5349
<TableHead>
5450
<TableRow>
55-
<TableCell width="40%">{t("table.icon")}</TableCell>
56-
<TableCell width="30%">{t("table.url")}</TableCell>
57-
<TableCell width="10%">{t("table.status")}</TableCell>
51+
<TableCell width="40%">Proxy</TableCell>
52+
<TableCell width="30%">URL</TableCell>
53+
<TableCell width="10%">Status</TableCell>
5854
</TableRow>
5955
</TableHead>
6056
<TableBody>
@@ -63,11 +59,11 @@ export const WorkspaceProxyPageView: FC<
6359
<TableLoader />
6460
</Cond>
6561
<Cond condition={hasLoaded && proxies?.length === 0}>
66-
<TableEmpty message={t("emptyState")} />
62+
<TableEmpty message="No workspace proxies found" />
6763
</Cond>
6864
<Cond>
6965
{proxies?.map((proxy) => (
70-
<ProxyRow
66+
< ProxyRow
7167
key={proxy.id}
7268
proxy={proxy}
7369
onSelectRegion={onSelect}

0 commit comments

Comments
 (0)