refactor: remove supabase auth
This commit is contained in:
@@ -26,7 +26,7 @@ export function Auth({ setIsMagicLinkSent }: AuthProps) {
|
||||
watch,
|
||||
formState: { errors },
|
||||
} = useForm<FormValues>({
|
||||
resolver: zodResolver(EmailSchema), // Apply the zodResolver
|
||||
resolver: zodResolver(EmailSchema),
|
||||
});
|
||||
|
||||
const email = watch("email");
|
||||
@@ -37,22 +37,21 @@ export function Auth({ setIsMagicLinkSent }: AuthProps) {
|
||||
},
|
||||
});
|
||||
|
||||
const loginWithOAuth = api.auth.loginWithOAuth.useMutation({
|
||||
onSuccess: (data) => {
|
||||
if (data.url) window.open(data.url);
|
||||
},
|
||||
});
|
||||
const handleLoginWithEmail = async (email: string) => {
|
||||
const { data, error } = await authClient.signIn.magicLink({
|
||||
email,
|
||||
callbackURL: "/boards",
|
||||
});
|
||||
|
||||
const onSubmit = (values: FormValues) => {
|
||||
try {
|
||||
loginWithEmail.mutate({
|
||||
email: values.email,
|
||||
});
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
if (!error) {
|
||||
setIsMagicLinkSent(true, email);
|
||||
}
|
||||
};
|
||||
|
||||
const onSubmit = async (values: FormValues) => {
|
||||
await handleLoginWithEmail(values.email);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="space-y-6">
|
||||
<div>
|
||||
@@ -80,12 +79,12 @@ export function Auth({ setIsMagicLinkSent }: AuthProps) {
|
||||
{...register("email", { required: true })}
|
||||
placeholder="Enter your email address"
|
||||
/>
|
||||
{!loginWithEmail.error && !loginWithOAuth.error && errors.email && (
|
||||
{!loginWithEmail.error && errors.email && (
|
||||
<p className="mt-2 text-xs text-red-400">
|
||||
Please enter a valid email address
|
||||
</p>
|
||||
)}
|
||||
{(loginWithEmail.error ?? loginWithOAuth.error) ? (
|
||||
{loginWithEmail.error ? (
|
||||
<p className="mt-2 text-xs text-red-400">
|
||||
Something went wrong, please try again later or contact customer
|
||||
support.
|
||||
|
||||
@@ -3,9 +3,9 @@ import { useRouter } from "next/navigation";
|
||||
import { Menu, Transition } from "@headlessui/react";
|
||||
import { Fragment } from "react";
|
||||
|
||||
import { authClient } from "@kan/auth";
|
||||
|
||||
import { useTheme } from "~/providers/theme";
|
||||
import createClient from "~/utils/supabase/client";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
|
||||
interface UserMenuProps {
|
||||
imageUrl: string | undefined;
|
||||
@@ -22,17 +22,17 @@ export default function UserMenu({
|
||||
email,
|
||||
isLoading,
|
||||
}: UserMenuProps) {
|
||||
const db = createClient();
|
||||
const router = useRouter();
|
||||
const { themePreference, switchTheme } = useTheme();
|
||||
|
||||
const handleLogout = async () => {
|
||||
await db.auth.signOut();
|
||||
await authClient.signOut();
|
||||
|
||||
router.push("/login");
|
||||
};
|
||||
|
||||
const avatarUrl = imageUrl ? getPublicUrl(imageUrl) : null;
|
||||
// const avatarUrl = imageUrl ? getPublicUrl(imageUrl) : null;
|
||||
const avatarUrl = "";
|
||||
|
||||
return (
|
||||
<Menu as="div" className="relative inline-block w-full text-left">
|
||||
|
||||
@@ -25,19 +25,15 @@ export const env = createEnv({
|
||||
* For them to be exposed to the client, prefix them with `NEXT_PUBLIC_`.
|
||||
*/
|
||||
client: {
|
||||
NEXT_PUBLIC_SUPABASE_AUTH_COOKIE_NAME: z.string(),
|
||||
NEXT_PUBLIC_SUPABASE_STORAGE_URL: z.string(),
|
||||
NEXT_PUBLIC_KAN_ENV: z.string(),
|
||||
NEXT_PUBLIC_UMAMI_ID: z.string().optional(),
|
||||
},
|
||||
/**
|
||||
* Destructure all variables from `process.env` to make sure they aren't tree-shaken away.
|
||||
*/
|
||||
experimental__runtimeEnv: {
|
||||
NEXT_PUBLIC_KAN_ENV: process.env.NEXT_PUBLIC_KAN_ENV,
|
||||
NODE_ENV: process.env.NODE_ENV,
|
||||
NEXT_PUBLIC_SUPABASE_AUTH_COOKIE_NAME:
|
||||
process.env.NEXT_PUBLIC_SUPABASE_AUTH_COOKIE_NAME,
|
||||
NEXT_PUBLIC_SUPABASE_STORAGE_URL:
|
||||
process.env.NEXT_PUBLIC_SUPABASE_STORAGE_URL,
|
||||
NEXT_PUBLIC_UMAMI_ID: process.env.NEXT_PUBLIC_UMAMI_ID,
|
||||
},
|
||||
skipValidation:
|
||||
|
||||
@@ -4,3 +4,7 @@ import { auth } from "@kan/auth";
|
||||
|
||||
export const config = { api: { bodyParser: false } };
|
||||
export default toNodeHandler(auth.handler);
|
||||
|
||||
// export const runtime = "edge";
|
||||
// export const preferredRegion = "lhr1";
|
||||
// export const dynamic = "force-dynamic";
|
||||
|
||||
@@ -1,112 +1,102 @@
|
||||
import type { EmailOtpType } from "@supabase/supabase-js";
|
||||
import type { NextRequest } from "next/server";
|
||||
import { NextResponse } from "next/server";
|
||||
import { Stripe } from "stripe";
|
||||
// import type { EmailOtpType } from "@supabase/supabase-js";
|
||||
// import type { NextRequest } from "next/server";
|
||||
// import { NextResponse } from "next/server";
|
||||
|
||||
import { createDrizzleClient } from "@kan/db/client";
|
||||
import * as memberRepo from "@kan/db/repository/member.repo";
|
||||
import * as userRepo from "@kan/db/repository/user.repo";
|
||||
import { createNextClient } from "@kan/supabase/clients";
|
||||
// import { createDrizzleClient } from "@kan/db/client";
|
||||
// import * as memberRepo from "@kan/db/repository/member.repo";
|
||||
// import * as userRepo from "@kan/db/repository/user.repo";
|
||||
// import { stripe } from "@kan/stripe";
|
||||
// import { createNextApiClient } from "@kan/";
|
||||
|
||||
const stripeSecretKey = process.env.STRIPE_SECRET_KEY;
|
||||
// export default async function handler(req: NextRequest) {
|
||||
// if (req.method !== "GET") {
|
||||
// return new NextResponse(null, {
|
||||
// status: 405,
|
||||
// headers: { Allow: "GET" },
|
||||
// });
|
||||
// }
|
||||
|
||||
if (!stripeSecretKey) {
|
||||
throw new Error("STRIPE_SECRET_KEY is not defined");
|
||||
}
|
||||
// if (!req.url) {
|
||||
// return new NextResponse(null, {
|
||||
// status: 400,
|
||||
// });
|
||||
// }
|
||||
|
||||
const stripe = new Stripe(stripeSecretKey, {
|
||||
apiVersion: "2024-12-18.acacia",
|
||||
});
|
||||
// const url = new URL(req.url);
|
||||
// const queryParams = Object.fromEntries(url.searchParams.entries());
|
||||
|
||||
export default async function handler(req: NextRequest) {
|
||||
if (req.method !== "GET") {
|
||||
return new NextResponse(null, {
|
||||
status: 405,
|
||||
headers: { Allow: "GET" },
|
||||
});
|
||||
}
|
||||
// const tokenHash = queryParams.token_hash;
|
||||
// const type = queryParams.type;
|
||||
// const code = queryParams.code;
|
||||
// const memberPublicId = queryParams.memberPublicId;
|
||||
|
||||
if (!req.url) {
|
||||
return new NextResponse(null, {
|
||||
status: 400,
|
||||
});
|
||||
}
|
||||
// let next = "/error";
|
||||
|
||||
const url = new URL(req.url);
|
||||
const queryParams = Object.fromEntries(url.searchParams.entries());
|
||||
// let authRes;
|
||||
|
||||
const tokenHash = queryParams.token_hash;
|
||||
const type = queryParams.type;
|
||||
const code = queryParams.code;
|
||||
const memberPublicId = queryParams.memberPublicId;
|
||||
// const response = NextResponse.next();
|
||||
|
||||
let next = "/error";
|
||||
// if ((tokenHash && type) ?? code) {
|
||||
// const supabaseClient = createNextClient(req, response);
|
||||
|
||||
let authRes;
|
||||
// if (tokenHash && type) {
|
||||
// authRes = await supabaseClient.auth.verifyOtp({
|
||||
// type: type as EmailOtpType,
|
||||
// token_hash: tokenHash,
|
||||
// });
|
||||
// }
|
||||
|
||||
const response = NextResponse.next();
|
||||
// if (code) {
|
||||
// authRes = await supabaseClient.auth.exchangeCodeForSession(code);
|
||||
// }
|
||||
|
||||
if ((tokenHash && type) ?? code) {
|
||||
const supabaseClient = createNextClient(req, response);
|
||||
// const user = authRes?.data.user;
|
||||
|
||||
if (tokenHash && type) {
|
||||
authRes = await supabaseClient.auth.verifyOtp({
|
||||
type: type as EmailOtpType,
|
||||
token_hash: tokenHash,
|
||||
});
|
||||
}
|
||||
// const db = createDrizzleClient();
|
||||
|
||||
if (code) {
|
||||
authRes = await supabaseClient.auth.exchangeCodeForSession(code);
|
||||
}
|
||||
// if (user?.id && user.email) {
|
||||
// const existingUser = await userRepo.getById(db, user.id);
|
||||
|
||||
const user = authRes?.data.user;
|
||||
// if (!existingUser) {
|
||||
// const stripeCustomer = await stripe.customers.create({
|
||||
// email: user.email,
|
||||
// metadata: {
|
||||
// userId: user.id,
|
||||
// },
|
||||
// });
|
||||
|
||||
const db = createDrizzleClient();
|
||||
// await userRepo.create(db, {
|
||||
// id: user.id,
|
||||
// email: user.email,
|
||||
// stripeCustomerId: stripeCustomer.id,
|
||||
// });
|
||||
// }
|
||||
// }
|
||||
|
||||
if (user?.id && user.email) {
|
||||
const existingUser = await userRepo.getById(db, user.id);
|
||||
// if (memberPublicId) {
|
||||
// const member = await memberRepo.getByPublicId(db, memberPublicId);
|
||||
|
||||
if (!existingUser) {
|
||||
const stripeCustomer = await stripe.customers.create({
|
||||
email: user.email,
|
||||
metadata: {
|
||||
userId: user.id,
|
||||
},
|
||||
});
|
||||
// if (member?.id) {
|
||||
// await memberRepo.acceptInvite(db, member.id);
|
||||
// }
|
||||
// }
|
||||
|
||||
await userRepo.create(db, {
|
||||
id: user.id,
|
||||
email: user.email,
|
||||
stripeCustomerId: stripeCustomer.id,
|
||||
});
|
||||
}
|
||||
}
|
||||
// if (authRes?.error) {
|
||||
// console.error(authRes.error);
|
||||
// } else {
|
||||
// next = queryParams.next ?? "/boards";
|
||||
// }
|
||||
// }
|
||||
|
||||
if (memberPublicId) {
|
||||
const member = await memberRepo.getByPublicId(db, memberPublicId);
|
||||
// const redirectResponse = NextResponse.redirect(new URL(next, req.url));
|
||||
|
||||
if (member?.id) {
|
||||
await memberRepo.acceptInvite(db, member.id);
|
||||
}
|
||||
}
|
||||
// response.headers.getSetCookie().forEach((cookie) => {
|
||||
// redirectResponse.headers.append("Set-Cookie", cookie);
|
||||
// });
|
||||
|
||||
if (authRes?.error) {
|
||||
console.error(authRes.error);
|
||||
} else {
|
||||
next = queryParams.next ?? "/boards";
|
||||
}
|
||||
}
|
||||
// return redirectResponse;
|
||||
// }
|
||||
|
||||
const redirectResponse = NextResponse.redirect(new URL(next, req.url));
|
||||
|
||||
response.headers.getSetCookie().forEach((cookie) => {
|
||||
redirectResponse.headers.append("Set-Cookie", cookie);
|
||||
});
|
||||
|
||||
return redirectResponse;
|
||||
}
|
||||
|
||||
export const runtime = "edge";
|
||||
export const preferredRegion = "lhr1";
|
||||
export const dynamic = "force-dynamic";
|
||||
// export const runtime = "edge";
|
||||
// export const preferredRegion = "lhr1";
|
||||
// export const dynamic = "force-dynamic";
|
||||
|
||||
@@ -1,22 +1,11 @@
|
||||
import type { NextRequest } from "next/server";
|
||||
import { NextResponse } from "next/server";
|
||||
import { Stripe } from "stripe";
|
||||
|
||||
import { createDrizzleClient } from "@kan/db/client";
|
||||
import * as userRepo from "@kan/db/repository/user.repo";
|
||||
import { createNextClient } from "@kan/supabase/clients";
|
||||
|
||||
const stripeSecretKey = process.env.STRIPE_SECRET_KEY;
|
||||
|
||||
if (!stripeSecretKey) {
|
||||
throw new Error("STRIPE_SECRET_KEY is not defined");
|
||||
}
|
||||
|
||||
const stripe = new Stripe(stripeSecretKey, {
|
||||
apiVersion: "2024-12-18.acacia",
|
||||
});
|
||||
import { createNextApiContext } from "@kan/api/trpc";
|
||||
import { createStripeClient } from "@kan/stripe";
|
||||
|
||||
export default async function handler(req: NextRequest) {
|
||||
const stripe = createStripeClient();
|
||||
|
||||
if (req.method !== "POST") {
|
||||
return new Response(JSON.stringify({ error: "Method not allowed" }), {
|
||||
status: 405,
|
||||
@@ -25,20 +14,7 @@ export default async function handler(req: NextRequest) {
|
||||
}
|
||||
|
||||
try {
|
||||
const response = NextResponse.next();
|
||||
const supabaseClient = createNextClient(req, response);
|
||||
const { data } = await supabaseClient.auth.getUser();
|
||||
|
||||
if (!data.user) {
|
||||
return new Response(JSON.stringify({ error: "Unauthorized" }), {
|
||||
status: 403,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
}
|
||||
|
||||
const db = createDrizzleClient();
|
||||
|
||||
const user = await userRepo.getById(db, data.user.id);
|
||||
const { user } = await createNextApiContext(req);
|
||||
|
||||
if (!user?.stripeCustomerId) {
|
||||
return new Response(
|
||||
|
||||
@@ -1,22 +1,9 @@
|
||||
import type { NextRequest } from "next/server";
|
||||
import { NextResponse } from "next/server";
|
||||
import { Stripe } from "stripe";
|
||||
import { z } from "zod";
|
||||
|
||||
import { createDrizzleClient } from "@kan/db/client";
|
||||
import * as userRepo from "@kan/db/repository/user.repo";
|
||||
import { createNextApiContext } from "@kan/api/trpc";
|
||||
import * as workspaceRepo from "@kan/db/repository/workspace.repo";
|
||||
import { createNextClient } from "@kan/supabase/clients";
|
||||
|
||||
const stripeSecretKey = process.env.STRIPE_SECRET_KEY;
|
||||
|
||||
if (!stripeSecretKey) {
|
||||
throw new Error("STRIPE_SECRET_KEY is not defined");
|
||||
}
|
||||
|
||||
const stripe = new Stripe(stripeSecretKey, {
|
||||
apiVersion: "2024-12-18.acacia",
|
||||
});
|
||||
import { createStripeClient } from "@kan/stripe";
|
||||
|
||||
const workspaceSlugSchema = z
|
||||
.string()
|
||||
@@ -33,6 +20,8 @@ interface CheckoutSessionRequest {
|
||||
}
|
||||
|
||||
export default async function handler(req: NextRequest) {
|
||||
const stripe = createStripeClient();
|
||||
|
||||
if (req.method !== "POST") {
|
||||
return new Response(JSON.stringify({ error: "Method not allowed" }), {
|
||||
status: 405,
|
||||
@@ -41,22 +30,7 @@ export default async function handler(req: NextRequest) {
|
||||
}
|
||||
|
||||
try {
|
||||
const response = NextResponse.next();
|
||||
|
||||
const supabaseClient = createNextClient(req, response);
|
||||
|
||||
const { data } = await supabaseClient.auth.getUser();
|
||||
|
||||
if (!data.user) {
|
||||
return new Response(JSON.stringify({ error: "Unauthorized" }), {
|
||||
status: 403,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
}
|
||||
|
||||
const db = createDrizzleClient();
|
||||
|
||||
const user = await userRepo.getById(db, data.user.id);
|
||||
const { user, db } = await createNextApiContext(req);
|
||||
|
||||
if (!user) {
|
||||
return new Response(JSON.stringify({ error: "User not found" }), {
|
||||
|
||||
@@ -1,24 +1,15 @@
|
||||
import type { NextRequest } from "next/server";
|
||||
import { NextResponse } from "next/server";
|
||||
import { Stripe } from "stripe";
|
||||
|
||||
import { createNextApiContext } from "@kan/api/trpc";
|
||||
import * as workspaceRepo from "@kan/db/repository/workspace.repo";
|
||||
import { createNextClient } from "@kan/supabase/clients";
|
||||
|
||||
const stripeSecretKey = process.env.STRIPE_SECRET_KEY;
|
||||
|
||||
if (!stripeSecretKey) {
|
||||
throw new Error("STRIPE_SECRET_KEY is not defined");
|
||||
}
|
||||
import { createStripeClient } from "@kan/stripe";
|
||||
|
||||
export const webCrypto = Stripe.createSubtleCryptoProvider();
|
||||
|
||||
const stripe: Stripe = new Stripe(stripeSecretKey, {
|
||||
apiVersion: "2024-12-18.acacia",
|
||||
httpClient: Stripe.createFetchHttpClient(),
|
||||
});
|
||||
|
||||
export default async function handler(req: NextRequest) {
|
||||
const stripe = createStripeClient();
|
||||
|
||||
if (req.method !== "POST") {
|
||||
return new Response(JSON.stringify({ message: "Method not allowed" }), {
|
||||
status: 405,
|
||||
@@ -44,9 +35,7 @@ export default async function handler(req: NextRequest) {
|
||||
webCrypto,
|
||||
);
|
||||
|
||||
const response = NextResponse.next();
|
||||
|
||||
const db = createNextClient(req, response);
|
||||
const { db } = await createNextApiContext(req);
|
||||
|
||||
switch (event.type) {
|
||||
case "checkout.session.completed": {
|
||||
|
||||
@@ -1,12 +0,0 @@
|
||||
import { createBrowserClient } from "@supabase/ssr";
|
||||
|
||||
import type { Database } from "@kan/db/types/database.types";
|
||||
|
||||
export default function createClient() {
|
||||
const supabase = createBrowserClient<Database>(
|
||||
process.env.NEXT_PUBLIC_SUPABASE_URL!,
|
||||
process.env.NEXT_PUBLIC_SUPABASE_ANON_KEY!,
|
||||
);
|
||||
|
||||
return supabase;
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
import createClient from "~/utils/supabase/client";
|
||||
|
||||
export const getPublicUrl = (fileName: string) => {
|
||||
const supabase = createClient();
|
||||
|
||||
return supabase.storage.from("avatars").getPublicUrl(fileName).data.publicUrl;
|
||||
};
|
||||
@@ -1,7 +1,6 @@
|
||||
import Avatar from "~/components/Avatar";
|
||||
import Badge from "~/components/Badge";
|
||||
import LabelIcon from "~/components/LabelIcon";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
|
||||
const Card = ({
|
||||
title,
|
||||
@@ -32,9 +31,7 @@ const Card = ({
|
||||
{members.map(({ user }) => {
|
||||
if (!user) return null;
|
||||
|
||||
const avatarUrl = user.image
|
||||
? getPublicUrl(user.image)
|
||||
: undefined;
|
||||
const avatarUrl = user.image ? "" : undefined;
|
||||
|
||||
return (
|
||||
<Avatar
|
||||
|
||||
@@ -11,7 +11,6 @@ import Button from "~/components/Button";
|
||||
import CheckboxDropdown from "~/components/CheckboxDropdown";
|
||||
import LabelIcon from "~/components/LabelIcon";
|
||||
import { formatMemberDisplayName, formatToArray } from "~/utils/helpers";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
|
||||
interface Member {
|
||||
publicId: string;
|
||||
@@ -66,9 +65,7 @@ const Filters = ({
|
||||
<Avatar
|
||||
size="xs"
|
||||
name={member.user?.name ?? ""}
|
||||
imageUrl={
|
||||
member.user?.image ? getPublicUrl(member.user.image) : undefined
|
||||
}
|
||||
imageUrl={member.user?.image ? "" : undefined}
|
||||
email={member.user?.email ?? ""}
|
||||
/>
|
||||
),
|
||||
|
||||
@@ -19,7 +19,6 @@ import { useModal } from "~/providers/modal";
|
||||
import { usePopup } from "~/providers/popup";
|
||||
import { api } from "~/utils/api";
|
||||
import { formatMemberDisplayName } from "~/utils/helpers";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
|
||||
type NewCardFormInput = NewCardInput & {
|
||||
isCreateAnotherEnabled: boolean;
|
||||
@@ -89,7 +88,7 @@ export function NewCardForm({
|
||||
args.labelPublicIds.includes(label.publicId),
|
||||
),
|
||||
members:
|
||||
oldBoard.workspace?.members.filter((member) =>
|
||||
oldBoard.workspace.members.filter((member) =>
|
||||
args.memberPublicIds.includes(member.publicId),
|
||||
) ?? [],
|
||||
_filteredLabels: labelPublicIds.map((id) => ({ publicId: id })),
|
||||
@@ -146,20 +145,18 @@ export function NewCardForm({
|
||||
})) ?? [];
|
||||
|
||||
const formattedMembers =
|
||||
boardData?.workspace?.members.map((member) => ({
|
||||
boardData?.workspace.members.map((member) => ({
|
||||
key: member.publicId,
|
||||
value: formatMemberDisplayName(
|
||||
member.user?.name ?? null,
|
||||
member.user?.email ?? null,
|
||||
member.user.name ?? null,
|
||||
member.user.email ?? null,
|
||||
),
|
||||
leftIcon: (
|
||||
<Avatar
|
||||
size="xs"
|
||||
name={member.user?.name ?? ""}
|
||||
imageUrl={
|
||||
member.user?.image ? getPublicUrl(member.user.image) : undefined
|
||||
}
|
||||
email={member.user?.email ?? ""}
|
||||
name={member.user.name ?? ""}
|
||||
imageUrl={member.user.image ? "" : undefined}
|
||||
email={member.user.email ?? ""}
|
||||
/>
|
||||
),
|
||||
})) ?? [];
|
||||
|
||||
@@ -15,7 +15,6 @@ import { usePopup } from "~/providers/popup";
|
||||
import { useWorkspace } from "~/providers/workspace";
|
||||
import { api } from "~/utils/api";
|
||||
import { formatMemberDisplayName } from "~/utils/helpers";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
import { DeleteLabelConfirmation } from "../../components/DeleteLabelConfirmation";
|
||||
import ActivityList from "./components/ActivityList";
|
||||
import { DeleteCardConfirmation } from "./components/DeleteCardConfirmation";
|
||||
@@ -51,11 +50,11 @@ export default function CardPage() {
|
||||
if (cardId) await utils.card.byId.refetch({ cardPublicId: cardId });
|
||||
};
|
||||
|
||||
const board = card?.list?.board;
|
||||
const board = card?.list.board;
|
||||
const boardId = board?.publicId;
|
||||
const labels = board?.labels;
|
||||
const activities = card?.activities;
|
||||
const workspaceMembers = board?.workspace?.members;
|
||||
const workspaceMembers = board?.workspace.members;
|
||||
const selectedLabels = card?.labels;
|
||||
const selectedMembers = card?.members;
|
||||
|
||||
@@ -77,7 +76,7 @@ export default function CardPage() {
|
||||
board?.lists.map((list) => ({
|
||||
key: list.publicId,
|
||||
value: list.name,
|
||||
selected: list.publicId === card?.list?.publicId,
|
||||
selected: list.publicId === card?.list.publicId,
|
||||
})) ?? [];
|
||||
|
||||
const formattedMembers =
|
||||
@@ -89,21 +88,21 @@ export default function CardPage() {
|
||||
return {
|
||||
key: member.publicId,
|
||||
value: formatMemberDisplayName(
|
||||
member.user?.name ?? null,
|
||||
member.user?.email ?? null,
|
||||
member.user.name ?? null,
|
||||
member.user.email ?? null,
|
||||
),
|
||||
imageUrl: member.user?.image
|
||||
imageUrl: member.user.image
|
||||
? getPublicUrl(member.user.image)
|
||||
: undefined,
|
||||
selected: isSelected ?? false,
|
||||
leftIcon: (
|
||||
<Avatar
|
||||
size="xs"
|
||||
name={member.user?.name ?? ""}
|
||||
name={member.user.name ?? ""}
|
||||
imageUrl={
|
||||
member.user?.image ? getPublicUrl(member.user.image) : undefined
|
||||
member.user.image ? getPublicUrl(member.user.image) : undefined
|
||||
}
|
||||
email={member.user?.email ?? ""}
|
||||
email={member.user.email ?? ""}
|
||||
/>
|
||||
),
|
||||
};
|
||||
|
||||
@@ -12,9 +12,11 @@ export default function Layout({ children }: { children: React.ReactNode }) {
|
||||
|
||||
const token =
|
||||
typeof window !== "undefined"
|
||||
? Cookies.get(env.NEXT_PUBLIC_SUPABASE_AUTH_COOKIE_NAME)
|
||||
? Cookies.get('kan.session_token')
|
||||
: null;
|
||||
|
||||
const getSession = async () => {
|
||||
|
||||
const { data } = api.user.getUser.useQuery(undefined, {
|
||||
enabled: !!token,
|
||||
});
|
||||
|
||||
@@ -11,7 +11,6 @@ import { useModal } from "~/providers/modal";
|
||||
import { useWorkspace } from "~/providers/workspace";
|
||||
import { api } from "~/utils/api";
|
||||
import { getInitialsFromName, inferInitialsFromEmail } from "~/utils/helpers";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
import { DeleteMemberConfirmation } from "./components/DeleteMemberConfirmation";
|
||||
import { InviteMemberForm } from "./components/InviteMemberForm";
|
||||
|
||||
@@ -58,7 +57,7 @@ export default function MembersPage() {
|
||||
<Avatar
|
||||
name={memberName ?? ""}
|
||||
email={memberEmail ?? ""}
|
||||
imageUrl={memberImage ? getPublicUrl(memberImage) : undefined}
|
||||
imageUrl={memberImage ? "" : undefined}
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
@@ -189,9 +188,9 @@ export default function MembersPage() {
|
||||
<TableRow
|
||||
key={member.publicId}
|
||||
memberPublicId={member.publicId}
|
||||
memberName={member.user?.name}
|
||||
memberEmail={member.user?.email}
|
||||
memberImage={member.user?.image}
|
||||
memberName={member.user.name}
|
||||
memberEmail={member.user.email}
|
||||
memberImage={member.user.image}
|
||||
memberRole={member.role}
|
||||
memberStatus={member.status}
|
||||
isLastRow={index === data.members.length - 1}
|
||||
|
||||
@@ -3,8 +3,6 @@ import { useState } from "react";
|
||||
|
||||
import { usePopup } from "~/providers/popup";
|
||||
import { api } from "~/utils/api";
|
||||
import createClient from "~/utils/supabase/client";
|
||||
import { getPublicUrl } from "~/utils/supabase/getPublicUrl";
|
||||
|
||||
export default function Avatar({
|
||||
userId,
|
||||
@@ -13,7 +11,6 @@ export default function Avatar({
|
||||
userId: string | undefined;
|
||||
userImage: string | null | undefined;
|
||||
}) {
|
||||
const supabase = createClient();
|
||||
const utils = api.useUtils();
|
||||
const { showPopup } = usePopup();
|
||||
const [uploading, setUploading] = useState(false);
|
||||
@@ -41,7 +38,7 @@ export default function Avatar({
|
||||
},
|
||||
});
|
||||
|
||||
const avatarUrl = userImage ? getPublicUrl(userImage) : undefined;
|
||||
const avatarUrl = userImage ? "" : undefined;
|
||||
|
||||
const uploadAvatar = async (event: React.ChangeEvent<HTMLInputElement>) => {
|
||||
try {
|
||||
@@ -65,13 +62,13 @@ export default function Avatar({
|
||||
const fileName = `${userId}/avatar.${fileExt}`;
|
||||
const filePath = `${fileName}`;
|
||||
|
||||
const { error: uploadError } = await supabase.storage
|
||||
.from("avatars")
|
||||
.upload(filePath, file, { upsert: true });
|
||||
// const { error: uploadError } = await supabase.storage
|
||||
// .from("avatars")
|
||||
// .upload(filePath, file, { upsert: true });
|
||||
|
||||
if (uploadError) {
|
||||
throw uploadError;
|
||||
}
|
||||
// if (uploadError) {
|
||||
// throw uploadError;
|
||||
// }
|
||||
|
||||
updateUser.mutate({ image: filePath });
|
||||
} catch (error) {
|
||||
|
||||
Reference in New Issue
Block a user