Skip to content

Commit

Permalink
feat: Enable custom domains for shareable links
Browse files Browse the repository at this point in the history
  • Loading branch information
richiemcilroy committed Feb 10, 2025
1 parent b8367cc commit c6aac14
Show file tree
Hide file tree
Showing 5 changed files with 68 additions and 5 deletions.
2 changes: 1 addition & 1 deletion apps/web/app/dashboard/caps/components/CapCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,7 @@ export const CapCard: React.FC<CapCardProps> = ({
className="group block"
href={
activeSpace?.space.customDomain
? `https://${activeSpace.space.customDomain}/${cap.id}`
? `https://${activeSpace.space.customDomain}/s/${cap.id}`
: clientEnv.NEXT_PUBLIC_IS_CAP && NODE_ENV === "production"
? `https://cap.link/${cap.id}`
: `${clientEnv.NEXT_PUBLIC_WEB_URL}/s/${cap.id}`
Expand Down
7 changes: 5 additions & 2 deletions apps/web/app/dashboard/caps/components/CapCardActions.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { serverEnv, clientEnv, NODE_ENV } from "@cap/env";
import { LinkIcon, Trash } from "lucide-react";
import { toast } from "react-hot-toast";
import { Tooltip } from "react-tooltip";

import { useSharedContext } from "../../_components/DynamicSharedLayout";
interface CapCardActionsProps {
capId: string;
onDelete: (videoId: string) => Promise<void>;
Expand All @@ -12,9 +12,12 @@ export const CapCardActions: React.FC<CapCardActionsProps> = ({
capId,
onDelete,
}) => {
const { activeSpace } = useSharedContext();
const copyLink = () => {
const link =
clientEnv.NEXT_PUBLIC_IS_CAP && NODE_ENV === "production"
activeSpace?.space.customDomain && activeSpace.space.domainVerified
? `https://${activeSpace.space.customDomain}/s/${capId}`
: clientEnv.NEXT_PUBLIC_IS_CAP && NODE_ENV === "production"
? `https://cap.link/${capId}`
: `${clientEnv.NEXT_PUBLIC_WEB_URL}/s/${capId}`;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,8 @@ export const SharedCapCard: React.FC<SharedCapCardProps> = ({
<a
className="group block"
href={
activeSpace?.space.customDomain
? `https://${activeSpace.space.customDomain}/${cap.id}`
activeSpace?.space.customDomain && activeSpace.space.domainVerified
? `https://${activeSpace.space.customDomain}/s/${cap.id}`
: clientEnv.NEXT_PUBLIC_IS_CAP && NODE_ENV === "production"
? `https://cap.link/${cap.id}`
: `${clientEnv.NEXT_PUBLIC_WEB_URL}/s/${cap.id}`
Expand Down
50 changes: 50 additions & 0 deletions apps/web/middleware.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import { NextResponse } from 'next/server';
import type { NextRequest } from 'next/server';
import { db } from '@cap/database';
import { spaces } from '@cap/database/schema';
import { eq } from 'drizzle-orm';

export async function middleware(request: NextRequest) {
const hostname = request.headers.get('host');
const path = request.nextUrl.pathname;

if (!hostname) return NextResponse.next();

// Skip for main domains
if (hostname.includes('cap.so') || hostname.includes('cap.link') || hostname.includes('localhost')) {
return NextResponse.next();
}

// We're on a custom domain at this point
// Only allow /s/ routes for custom domains
if (!path.startsWith('/s/')) {
const url = new URL(request.url);
url.hostname = 'cap.so';
return NextResponse.redirect(url);
}

try {
// Query the space with this custom domain
const [space] = await db
.select()
.from(spaces)
.where(eq(spaces.customDomain, hostname));

if (!space || !space.domainVerified) {
// If no verified custom domain found, redirect to main domain
const url = new URL(request.url);
url.hostname = 'cap.so';
return NextResponse.redirect(url);
}

// Allow the request to continue to the destination
return NextResponse.next();
} catch (error) {
console.error('Error in middleware:', error);
return NextResponse.next();
}
}

export const config = {
matcher: ['/((?!api|_next/static|_next/image|favicon.ico).*)']
};
10 changes: 10 additions & 0 deletions apps/web/next.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,16 @@ const nextConfig = {
source: "/r/:path*",
destination: "https://dub.cap.link/:path*",
},
{
source: '/s/:videoId',
destination: '/s/:videoId',
has: [
{
type: 'host',
value: '(?!cap\.so|cap\.link).*',
},
],
}
];
},
async redirects() {
Expand Down

1 comment on commit c6aac14

@vercel
Copy link

@vercel vercel bot commented on c6aac14 Feb 10, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.