mirror of
https://github.com/fosrl/pangolin.git
synced 2026-05-22 00:35:22 +00:00
Merge branch 'dev' into alerting-rules
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
import { Request, Response, NextFunction } from "express";
|
||||
import { z } from "zod";
|
||||
import { db, orgs, userOrgs, users } from "@server/db";
|
||||
import { eq, and, inArray } from "drizzle-orm";
|
||||
import { eq, and, inArray, not } from "drizzle-orm";
|
||||
import response from "@server/lib/response";
|
||||
import HttpCode from "@server/types/HttpCode";
|
||||
import createHttpError from "http-errors";
|
||||
@@ -17,11 +17,10 @@ import { verifyTotpCode } from "@server/auth/totp";
|
||||
import { calculateUserClientsForOrgs } from "@server/lib/calculateUserClientsForOrgs";
|
||||
import { build } from "@server/build";
|
||||
import { getOrgTierData } from "#dynamic/lib/billing";
|
||||
import {
|
||||
deleteOrgById,
|
||||
sendTerminationMessages
|
||||
} from "@server/lib/deleteOrg";
|
||||
import { deleteOrgById, sendTerminationMessages } from "@server/lib/deleteOrg";
|
||||
import { UserType } from "@server/types/UserTypes";
|
||||
import { usageService } from "@server/lib/billing/usageService";
|
||||
import { FeatureId } from "@server/lib/billing";
|
||||
|
||||
const deleteMyAccountBody = z.strictObject({
|
||||
password: z.string().optional(),
|
||||
@@ -98,9 +97,9 @@ export async function deleteMyAccount(
|
||||
and(eq(userOrgs.userId, userId), eq(userOrgs.isOwner, true))
|
||||
);
|
||||
|
||||
const orgIds = ownedOrgsRows.map((r) => r.orgId);
|
||||
const ownedOrgIds = ownedOrgsRows.map((r) => r.orgId);
|
||||
|
||||
if (build === "saas" && orgIds.length > 0) {
|
||||
if (build === "saas" && ownedOrgIds.length > 0) {
|
||||
const primaryOrgId = ownedOrgsRows.find(
|
||||
(r) => r.isBillingOrg && r.isOwner
|
||||
)?.orgId;
|
||||
@@ -119,14 +118,14 @@ export async function deleteMyAccount(
|
||||
|
||||
if (!password) {
|
||||
const orgsWithNames =
|
||||
orgIds.length > 0
|
||||
ownedOrgIds.length > 0
|
||||
? await db
|
||||
.select({
|
||||
orgId: orgs.orgId,
|
||||
name: orgs.name
|
||||
})
|
||||
.from(orgs)
|
||||
.where(inArray(orgs.orgId, orgIds))
|
||||
.where(inArray(orgs.orgId, ownedOrgIds))
|
||||
: [];
|
||||
return response<DeleteMyAccountPreviewResponse>(res, {
|
||||
data: {
|
||||
@@ -206,9 +205,23 @@ export async function deleteMyAccount(
|
||||
olmsToTerminate: allOlmsToTerminate
|
||||
});
|
||||
|
||||
const otherOrgsTheUserWasIn = await db
|
||||
.select()
|
||||
.from(userOrgs)
|
||||
.where(
|
||||
and(
|
||||
eq(userOrgs.userId, userId),
|
||||
not(inArray(userOrgs.orgId, ownedOrgIds))
|
||||
)
|
||||
);
|
||||
|
||||
await db.transaction(async (trx) => {
|
||||
await trx.delete(users).where(eq(users.userId, userId));
|
||||
await calculateUserClientsForOrgs(userId, trx);
|
||||
// loop through the other orgs and decrement the count
|
||||
for (const userOrg of otherOrgsTheUserWasIn) {
|
||||
await usageService.add(userOrg.orgId, FeatureId.USERS, -1, trx);
|
||||
}
|
||||
});
|
||||
|
||||
try {
|
||||
@@ -233,10 +246,7 @@ export async function deleteMyAccount(
|
||||
} catch (error) {
|
||||
logger.error(error);
|
||||
return next(
|
||||
createHttpError(
|
||||
HttpCode.INTERNAL_SERVER_ERROR,
|
||||
"An error occurred"
|
||||
)
|
||||
createHttpError(HttpCode.INTERNAL_SERVER_ERROR, "An error occurred")
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,10 +24,8 @@ import dynamic from "next/dynamic";
|
||||
import Link from "next/link";
|
||||
import { usePathname } from "next/navigation";
|
||||
import { useEffect, useState } from "react";
|
||||
import { FaGithub } from "react-icons/fa";
|
||||
import SidebarLicenseButton from "./SidebarLicenseButton";
|
||||
import { SidebarSupportButton } from "./SidebarSupportButton";
|
||||
import { is } from "drizzle-orm";
|
||||
|
||||
const ProductUpdates = dynamic(() => import("./ProductUpdates"), {
|
||||
ssr: false
|
||||
@@ -291,7 +289,6 @@ export function LayoutSidebar({
|
||||
: build === "enterprise"
|
||||
? t("enterpriseEdition")
|
||||
: "Pangolin Cloud"}
|
||||
<FaGithub size={12} />
|
||||
</Link>
|
||||
</div>
|
||||
{build === "enterprise" &&
|
||||
|
||||
@@ -103,29 +103,27 @@ export default function ProductUpdates({
|
||||
)}
|
||||
>
|
||||
<div className="flex flex-col gap-1">
|
||||
<small
|
||||
className={cn(
|
||||
"text-xs text-muted-foreground flex items-center gap-1 mt-2 empty:mt-0",
|
||||
showMoreUpdatesText
|
||||
? "animate-in fade-in duration-300"
|
||||
: "opacity-0"
|
||||
)}
|
||||
>
|
||||
{filteredUpdates.length > 1 && (
|
||||
<>
|
||||
<BellIcon className="flex-none size-3" />
|
||||
<span>
|
||||
{showNewVersionPopup
|
||||
? t("productUpdateMoreInfo", {
|
||||
noOfUpdates: filteredUpdates.length
|
||||
})
|
||||
: t("productUpdateInfo", {
|
||||
noOfUpdates: filteredUpdates.length
|
||||
})}
|
||||
</span>
|
||||
</>
|
||||
)}
|
||||
</small>
|
||||
{filteredUpdates.length > 1 && (
|
||||
<small
|
||||
className={cn(
|
||||
"text-xs text-muted-foreground flex items-center gap-1 mt-2",
|
||||
showMoreUpdatesText
|
||||
? "animate-in fade-in duration-300"
|
||||
: "opacity-0"
|
||||
)}
|
||||
>
|
||||
<BellIcon className="flex-none size-3" />
|
||||
<span>
|
||||
{showNewVersionPopup
|
||||
? t("productUpdateMoreInfo", {
|
||||
noOfUpdates: filteredUpdates.length
|
||||
})
|
||||
: t("productUpdateInfo", {
|
||||
noOfUpdates: filteredUpdates.length
|
||||
})}
|
||||
</span>
|
||||
</small>
|
||||
)}
|
||||
<ProductUpdatesListPopup
|
||||
updates={filteredUpdates}
|
||||
show={filteredUpdates.length > 0}
|
||||
@@ -378,7 +376,7 @@ function NewVersionAvailable({
|
||||
<span>
|
||||
{t("pangolinUpdateAvailableReleaseNotes")}
|
||||
</span>
|
||||
<ArrowRight className="flex-none size-3 transition-transform duration-300 ease-in-out group-hover:translate-x-1" />
|
||||
<ArrowRight className="flex-none size-3" />
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
|
||||
Reference in New Issue
Block a user