mirror of
https://github.com/fosrl/pangolin.git
synced 2025-08-16 07:28:06 +02:00
protect /setup and use links for button
This commit is contained in:
parent
7c9e57ef12
commit
41e531306d
11 changed files with 48 additions and 63 deletions
|
@ -1,4 +1,4 @@
|
||||||
import { render } from "@react-email/components";
|
import { render } from "@react-email/render";
|
||||||
import { ReactElement } from "react";
|
import { ReactElement } from "react";
|
||||||
import emailClient from "@server/emails";
|
import emailClient from "@server/emails";
|
||||||
import logger from "@server/logger";
|
import logger from "@server/logger";
|
||||||
|
@ -21,7 +21,9 @@ export async function sendEmail(
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
logger.debug("Rendering email templatee...")
|
||||||
const emailHtml = await render(template);
|
const emailHtml = await render(template);
|
||||||
|
logger.debug("Done rendering email templatee")
|
||||||
|
|
||||||
const options = {
|
const options = {
|
||||||
from: opts.from,
|
from: opts.from,
|
||||||
|
|
|
@ -76,7 +76,7 @@ export function RolesDataTable<TData, TValue>({
|
||||||
}
|
}
|
||||||
className="w-full pl-8"
|
className="w-full pl-8"
|
||||||
/>
|
/>
|
||||||
<Search className="h-5 w-5 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
<Search className="h-4 w-4 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
||||||
</div>
|
</div>
|
||||||
<Button
|
<Button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
|
|
@ -76,7 +76,7 @@ export function UsersDataTable<TData, TValue>({
|
||||||
}
|
}
|
||||||
className="w-full pl-8"
|
className="w-full pl-8"
|
||||||
/>
|
/>
|
||||||
<Search className="h-5 w-5 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
<Search className="h-4 w-4 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
||||||
</div>
|
</div>
|
||||||
<Button
|
<Button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
|
|
@ -116,7 +116,10 @@ export default function UsersTable({ users: u }: UsersTableProps) {
|
||||||
<>
|
<>
|
||||||
<div className="flex items-center justify-end">
|
<div className="flex items-center justify-end">
|
||||||
{userRow.isOwner && (
|
{userRow.isOwner && (
|
||||||
<Button variant="ghost" className="opacity-0 cursor-default">
|
<Button
|
||||||
|
variant="ghost"
|
||||||
|
className="opacity-0 cursor-default"
|
||||||
|
>
|
||||||
Placeholder
|
Placeholder
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
|
@ -161,18 +164,17 @@ export default function UsersTable({ users: u }: UsersTableProps) {
|
||||||
)}
|
)}
|
||||||
</DropdownMenuContent>
|
</DropdownMenuContent>
|
||||||
</DropdownMenu>
|
</DropdownMenu>
|
||||||
|
<Link
|
||||||
|
href={`/${org?.org.orgId}/settings/access/users/${userRow.id}`}
|
||||||
|
>
|
||||||
<Button
|
<Button
|
||||||
variant={"gray"}
|
variant={"gray"}
|
||||||
className="ml-2"
|
className="ml-2"
|
||||||
onClick={() =>
|
|
||||||
router.push(
|
|
||||||
`/${org?.org.orgId}/settings/access/users/${userRow.id}`,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
>
|
>
|
||||||
Manage{" "}
|
Manage
|
||||||
<ArrowRight className="ml-2 w-4 h-4" />
|
<ArrowRight className="ml-2 w-4 h-4" />
|
||||||
</Button>
|
</Button>
|
||||||
|
</Link>
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -149,7 +149,7 @@ export default function Header({ email, orgId, name, orgs }: HeaderProps) {
|
||||||
size="lg"
|
size="lg"
|
||||||
role="combobox"
|
role="combobox"
|
||||||
aria-expanded={open}
|
aria-expanded={open}
|
||||||
className="w-full md:w-[200px] h-12 px-3 py-4 bg-neutral hover:bg-muted"
|
className="w-full md:w-[200px] h-12 px-3 py-4 bg-neutral hover:bg-neutral"
|
||||||
>
|
>
|
||||||
<div className="flex items-center justify-between w-full">
|
<div className="flex items-center justify-between w-full">
|
||||||
<div className="flex flex-col items-start">
|
<div className="flex flex-col items-start">
|
||||||
|
@ -202,29 +202,6 @@ export default function Header({ email, orgId, name, orgs }: HeaderProps) {
|
||||||
</Command>
|
</Command>
|
||||||
</PopoverContent>
|
</PopoverContent>
|
||||||
</Popover>
|
</Popover>
|
||||||
|
|
||||||
{/* <Select
|
|
||||||
defaultValue={orgId}
|
|
||||||
onValueChange={(val) => {
|
|
||||||
router.push(`/${val}/settings`);
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<SelectTrigger className="w-[100px] md:w-[180px]">
|
|
||||||
<SelectValue placeholder="Select an org" />
|
|
||||||
</SelectTrigger>
|
|
||||||
<SelectContent>
|
|
||||||
<SelectGroup>
|
|
||||||
{orgs.map((org) => (
|
|
||||||
<SelectItem
|
|
||||||
value={org.name}
|
|
||||||
key={org.orgId}
|
|
||||||
>
|
|
||||||
{org.name}
|
|
||||||
</SelectItem>
|
|
||||||
))}
|
|
||||||
</SelectGroup>
|
|
||||||
</SelectContent>
|
|
||||||
</Select> */}
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
|
|
|
@ -77,7 +77,7 @@ export function ResourcesDataTable<TData, TValue>({
|
||||||
}
|
}
|
||||||
className="w-full pl-8"
|
className="w-full pl-8"
|
||||||
/>
|
/>
|
||||||
<Search className="h-5 w-5 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
<Search className="h-4 w-4 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
||||||
</div>
|
</div>
|
||||||
<Button
|
<Button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
|
|
@ -253,17 +253,14 @@ export default function SitesTable({ resources, orgId }: ResourcesTableProps) {
|
||||||
</DropdownMenuItem>
|
</DropdownMenuItem>
|
||||||
</DropdownMenuContent>
|
</DropdownMenuContent>
|
||||||
</DropdownMenu>
|
</DropdownMenu>
|
||||||
<Button
|
<Link
|
||||||
variant={"gray"}
|
href={`/${resourceRow.orgId}/settings/resources/${resourceRow.id}`}
|
||||||
className="ml-2"
|
|
||||||
onClick={() =>
|
|
||||||
router.push(
|
|
||||||
`/${resourceRow.orgId}/settings/resources/${resourceRow.id}`,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
>
|
>
|
||||||
Edit <ArrowRight className="ml-2 w-4 h-4" />
|
<Button variant={"gray"} className="ml-2">
|
||||||
|
Edit
|
||||||
|
<ArrowRight className="ml-2 w-4 h-4" />
|
||||||
</Button>
|
</Button>
|
||||||
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|
|
@ -77,7 +77,7 @@ export function SitesDataTable<TData, TValue>({
|
||||||
}
|
}
|
||||||
className="w-full pl-8"
|
className="w-full pl-8"
|
||||||
/>
|
/>
|
||||||
<Search className="h-5 w-5 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
<Search className="h-4 w-4 absolute left-2 top-1/2 transform -translate-y-1/2" />
|
||||||
</div>
|
</div>
|
||||||
<Button
|
<Button
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
|
|
|
@ -202,17 +202,14 @@ export default function SitesTable({ sites, orgId }: SitesTableProps) {
|
||||||
</DropdownMenuItem>
|
</DropdownMenuItem>
|
||||||
</DropdownMenuContent>
|
</DropdownMenuContent>
|
||||||
</DropdownMenu>
|
</DropdownMenu>
|
||||||
<Button
|
<Link
|
||||||
variant={"gray"}
|
href={`/${siteRow.orgId}/settings/sites/${siteRow.nice}`}
|
||||||
className="ml-2"
|
|
||||||
onClick={() =>
|
|
||||||
router.push(
|
|
||||||
`/${siteRow.orgId}/settings/sites/${siteRow.nice}`,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
>
|
>
|
||||||
Edit <ArrowRight className="ml-2 w-4 h-4" />
|
<Button variant={"gray"} className="ml-2">
|
||||||
|
Edit
|
||||||
|
<ArrowRight className="ml-2 w-4 h-4" />
|
||||||
</Button>
|
</Button>
|
||||||
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
|
|
@ -1,4 +1,7 @@
|
||||||
|
import { verifySession } from "@app/lib/auth/verifySession";
|
||||||
import { Metadata } from "next";
|
import { Metadata } from "next";
|
||||||
|
import { redirect } from "next/navigation";
|
||||||
|
import { cache } from "react";
|
||||||
|
|
||||||
export const metadata: Metadata = {
|
export const metadata: Metadata = {
|
||||||
title: `Setup - Pangolin`,
|
title: `Setup - Pangolin`,
|
||||||
|
@ -10,5 +13,12 @@ export default async function SetupLayout({
|
||||||
}: {
|
}: {
|
||||||
children: React.ReactNode;
|
children: React.ReactNode;
|
||||||
}) {
|
}) {
|
||||||
|
const getUser = cache(verifySession);
|
||||||
|
const user = await getUser();
|
||||||
|
|
||||||
|
if (!user) {
|
||||||
|
redirect("/");
|
||||||
|
}
|
||||||
|
|
||||||
return <div className="mt-32">{children}</div>;
|
return <div className="mt-32">{children}</div>;
|
||||||
}
|
}
|
||||||
|
|
|
@ -44,7 +44,7 @@ export default function StepperForm() {
|
||||||
|
|
||||||
const debouncedCheckOrgIdAvailability = useCallback(
|
const debouncedCheckOrgIdAvailability = useCallback(
|
||||||
debounce(checkOrgIdAvailability, 300),
|
debounce(checkOrgIdAvailability, 300),
|
||||||
[checkOrgIdAvailability]
|
[checkOrgIdAvailability],
|
||||||
);
|
);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
@ -278,7 +278,7 @@ export default function StepperForm() {
|
||||||
|
|
||||||
function debounce<T extends (...args: any[]) => any>(
|
function debounce<T extends (...args: any[]) => any>(
|
||||||
func: T,
|
func: T,
|
||||||
wait: number
|
wait: number,
|
||||||
): (...args: Parameters<T>) => void {
|
): (...args: Parameters<T>) => void {
|
||||||
let timeout: NodeJS.Timeout | null = null;
|
let timeout: NodeJS.Timeout | null = null;
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue