+
+
{metadata.applicationName}
@@ -112,11 +123,11 @@ export function DeviceAuthConfirmation({
-
+
{t("deviceFullAccess")}
-
+
{t("deviceOrganizationsAccess")}
diff --git a/src/components/DeviceLoginForm.tsx b/src/components/DeviceLoginForm.tsx
index 77ed06449..57b60f3fd 100644
--- a/src/components/DeviceLoginForm.tsx
+++ b/src/components/DeviceLoginForm.tsx
@@ -268,6 +268,7 @@ export default function DeviceLoginForm({
return (
{
// Strip hyphens and convert to uppercase
diff --git a/src/components/PaidFeaturesAlert.tsx b/src/components/PaidFeaturesAlert.tsx
index f9ce12ea0..3b50e63e2 100644
--- a/src/components/PaidFeaturesAlert.tsx
+++ b/src/components/PaidFeaturesAlert.tsx
@@ -137,11 +137,16 @@ export function PaidFeaturesAlert({ tiers }: Props) {
{requiredTiersLabel
? t.rich("upgradeToTierToUse", {
tier: requiredTiersLabel,
- tierLink: tierLinkRenderer
+ tierLink: tierLinkRenderer,
+ bookADemoLink: bookADemoLinkRenderer
})
: isActive
- ? t("mustUpgradeToUse")
- : t("subscriptionRequiredToUse")}
+ ? t.rich("mustUpgradeToUse", {
+ bookADemoLink: bookADemoLinkRenderer
+ })
+ : t.rich("subscriptionRequiredToUse", {
+ bookADemoLink: bookADemoLinkRenderer
+ })}
diff --git a/src/components/PrivateResourcesTable.tsx b/src/components/PrivateResourcesTable.tsx
index 8c6281dd2..902faf434 100644
--- a/src/components/PrivateResourcesTable.tsx
+++ b/src/components/PrivateResourcesTable.tsx
@@ -357,6 +357,12 @@ export default function PrivateResourcesTable({
label: t(
"editInternalResourceDialogModeInference"
)
+ },
+ {
+ value: "gateway",
+ label: t(
+ "editInternalResourceDialogModeGateway"
+ )
}
]}
selectedValue={searchParams.get("mode") ?? undefined}
diff --git a/src/components/resource-launcher/LauncherResourceAccess.tsx b/src/components/resource-launcher/LauncherResourceAccess.tsx
index 81a867e17..71106c125 100644
--- a/src/components/resource-launcher/LauncherResourceAccess.tsx
+++ b/src/components/resource-launcher/LauncherResourceAccess.tsx
@@ -1,6 +1,7 @@
"use client";
import { isSafeUrlForLink } from "@app/lib/launcherResourceAccess";
+import { useTranslations } from "next-intl";
import Link from "next/link";
import { LauncherCopyIcon } from "./LauncherCopyIcon";
@@ -8,6 +9,7 @@ type LauncherResourceAccessProps = {
accessDisplay: string;
accessCopyValue: string;
accessUrl?: string | null;
+ mode?: string;
variant: "grid" | "list";
};
@@ -15,15 +17,23 @@ export function LauncherResourceAccess({
accessDisplay,
accessCopyValue,
accessUrl,
+ mode,
variant
}: LauncherResourceAccessProps) {
- if (!accessDisplay) {
+ const t = useTranslations();
+ const isExitNode = mode === "gateway";
+ const display = isExitNode
+ ? t("resourceLauncherAllInternetTraffic")
+ : accessDisplay;
+
+ if (!display) {
return null;
}
const href = accessUrl ?? undefined;
- const canLink = href && isSafeUrlForLink(href);
+ const canLink = !isExitNode && href && isSafeUrlForLink(href);
const copyValue = canLink ? href : accessCopyValue;
+ const showCopy = !isExitNode && Boolean(copyValue);
if (variant === "list") {
return (
@@ -35,14 +45,14 @@ export function LauncherResourceAccess({
rel="noopener noreferrer"
className="min-w-0 truncate text-sm text-muted-foreground hover:underline max-md:overflow-visible max-md:whitespace-nowrap"
>
- {accessDisplay}
+ {display}
) : (
- {accessDisplay}
+ {display}
)}
-
+ {showCopy ?
: null}
);
}
@@ -56,14 +66,14 @@ export function LauncherResourceAccess({
rel="noopener noreferrer"
className="min-w-0 flex-1 truncate text-sm text-muted-foreground hover:underline"
>
- {accessDisplay}
+ {display}
) : (