Better display when there are lots of dev environment (#1093)
* Created an EnvironmentLabels component that puts extra dev environments behind a + * Added new environment labels components to schedules pages
This commit is contained in:
@@ -1,5 +1,7 @@
|
||||
import { RuntimeEnvironment } from "~/models/runtimeEnvironment.server";
|
||||
import type { RuntimeEnvironment } from "~/models/runtimeEnvironment.server";
|
||||
import { cn } from "~/utils/cn";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
import { SimpleTooltip } from "../primitives/Tooltip";
|
||||
|
||||
type Environment = Pick<RuntimeEnvironment, "type">;
|
||||
const variants = {
|
||||
@@ -33,6 +35,73 @@ export function EnvironmentLabel({
|
||||
);
|
||||
}
|
||||
|
||||
type EnvironmentWithUsername = Environment & { userName?: string };
|
||||
|
||||
export function EnvironmentLabels({
|
||||
environments,
|
||||
size = "small",
|
||||
className,
|
||||
}: {
|
||||
environments: EnvironmentWithUsername[];
|
||||
size?: keyof typeof variants;
|
||||
className?: string;
|
||||
}) {
|
||||
const devEnvironments = sortEnvironments(
|
||||
environments.filter((env) => env.type === "DEVELOPMENT")
|
||||
);
|
||||
const firstDevEnvironment = devEnvironments[0];
|
||||
const otherDevEnvironments = devEnvironments.slice(1);
|
||||
const otherEnvironments = environments.filter((env) => env.type !== "DEVELOPMENT");
|
||||
|
||||
return (
|
||||
<div className={cn("flex items-baseline gap-2", className)}>
|
||||
{firstDevEnvironment && (
|
||||
<EnvironmentLabel
|
||||
environment={firstDevEnvironment}
|
||||
userName={firstDevEnvironment.userName}
|
||||
size={size}
|
||||
/>
|
||||
)}
|
||||
{otherDevEnvironments.length > 0 ? (
|
||||
<SimpleTooltip
|
||||
button={
|
||||
<span
|
||||
className={cn(
|
||||
"inline-flex items-center justify-center whitespace-nowrap border font-medium uppercase tracking-wider",
|
||||
environmentBorderClassName({ type: "DEVELOPMENT" }),
|
||||
environmentTextClassName({ type: "DEVELOPMENT" }),
|
||||
variants[size]
|
||||
)}
|
||||
>
|
||||
+{otherDevEnvironments.length}
|
||||
</span>
|
||||
}
|
||||
content={
|
||||
<div className="flex gap-1 py-1">
|
||||
{otherDevEnvironments.map((environment, index) => (
|
||||
<EnvironmentLabel
|
||||
key={index}
|
||||
environment={environment}
|
||||
userName={environment.userName}
|
||||
size={size}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
}
|
||||
/>
|
||||
) : null}
|
||||
{otherEnvironments.map((environment, index) => (
|
||||
<EnvironmentLabel
|
||||
key={index}
|
||||
environment={environment}
|
||||
userName={environment.userName}
|
||||
size={size}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export function environmentTitle(environment: Environment, username?: string) {
|
||||
switch (environment.type) {
|
||||
case "PRODUCTION":
|
||||
|
||||
@@ -14,7 +14,7 @@ import {
|
||||
IndexEndpointStats,
|
||||
parseEndpointIndexStats,
|
||||
} from "@trigger.dev/core";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
|
||||
export type Client = {
|
||||
slug: string;
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { z } from "zod";
|
||||
import { PrismaClient, prisma } from "~/db.server";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
import { httpEndpointUrl } from "~/services/httpendpoint/HandleHttpEndpointService";
|
||||
import { getSecretStore } from "~/services/secrets/secretStore.server";
|
||||
import { projectPath } from "~/utils/pathBuilder";
|
||||
|
||||
@@ -2,7 +2,7 @@ import { PrismaClient, prisma } from "~/db.server";
|
||||
import { Project } from "~/models/project.server";
|
||||
import { displayableEnvironments } from "~/models/runtimeEnvironment.server";
|
||||
import { User } from "~/models/user.server";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
|
||||
export class ProjectPresenter {
|
||||
#prismaClient: PrismaClient;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { PrismaClient, prisma } from "~/db.server";
|
||||
import { Project } from "~/models/project.server";
|
||||
import { User } from "~/models/user.server";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
|
||||
export class ApiKeysPresenter {
|
||||
#prismaClient: PrismaClient;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { PrismaClient, prisma } from "~/db.server";
|
||||
import { Project } from "~/models/project.server";
|
||||
import { User } from "~/models/user.server";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
import { EnvironmentVariablesRepository } from "~/v3/environmentVariables/environmentVariablesRepository.server";
|
||||
|
||||
type Result = Awaited<ReturnType<EnvironmentVariablesPresenter["call"]>>;
|
||||
|
||||
@@ -10,7 +10,7 @@ import { Organization } from "~/models/organization.server";
|
||||
import { Project } from "~/models/project.server";
|
||||
import { displayableEnvironments } from "~/models/runtimeEnvironment.server";
|
||||
import { User } from "~/models/user.server";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
import { logger } from "~/services/logger.server";
|
||||
import { BasePresenter } from "./basePresenter.server";
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { TaskTriggerSource } from "@trigger.dev/database";
|
||||
import { sqlDatabaseSchema, PrismaClient, prisma } from "~/db.server";
|
||||
import { TestSearchParams } from "~/routes/_app.orgs.$organizationSlug.projects.v3.$projectParam.test/route";
|
||||
import { sortEnvironments } from "~/services/environmentSort.server";
|
||||
import { sortEnvironments } from "~/utils/environmentSort";
|
||||
import { createSearchParams } from "~/utils/searchParams";
|
||||
import { getUsername } from "~/utils/username";
|
||||
|
||||
|
||||
+2
-10
@@ -11,7 +11,7 @@ import { InitCommandV3, TriggerDevStepV3, TriggerLoginStepV3 } from "~/component
|
||||
import { StepContentContainer } from "~/components/StepContentContainer";
|
||||
import { AdminDebugTooltip } from "~/components/admin/debugTooltip";
|
||||
import { InlineCode } from "~/components/code/InlineCode";
|
||||
import { EnvironmentLabel } from "~/components/environments/EnvironmentLabel";
|
||||
import { EnvironmentLabels } from "~/components/environments/EnvironmentLabel";
|
||||
import { MainCenteredContainer, PageBody, PageContainer } from "~/components/layout/AppLayout";
|
||||
import { Button } from "~/components/primitives/Buttons";
|
||||
import { Callout } from "~/components/primitives/Callout";
|
||||
@@ -261,15 +261,7 @@ export default function Page() {
|
||||
</Suspense>
|
||||
</TableCell>
|
||||
<TableCell to={path}>
|
||||
<div className="space-x-2">
|
||||
{task.environments.map((environment) => (
|
||||
<EnvironmentLabel
|
||||
key={environment.id}
|
||||
environment={environment}
|
||||
userName={environment.userName}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
<EnvironmentLabels environments={task.environments} />
|
||||
</TableCell>
|
||||
<TableCellChevron to={path} />
|
||||
</TableRow>
|
||||
|
||||
+2
-11
@@ -8,7 +8,7 @@ import { typedjson, useTypedLoaderData } from "remix-typedjson";
|
||||
import { z } from "zod";
|
||||
import { ExitIcon } from "~/assets/icons/ExitIcon";
|
||||
import { InlineCode } from "~/components/code/InlineCode";
|
||||
import { EnvironmentLabel } from "~/components/environments/EnvironmentLabel";
|
||||
import { EnvironmentLabel, EnvironmentLabels } from "~/components/environments/EnvironmentLabel";
|
||||
import { Button, LinkButton } from "~/components/primitives/Buttons";
|
||||
import { DateTime } from "~/components/primitives/DateTime";
|
||||
import {
|
||||
@@ -211,16 +211,7 @@ export default function Page() {
|
||||
</div>
|
||||
</Property>
|
||||
<Property label="Environments">
|
||||
<div className="flex flex-wrap gap-1">
|
||||
{schedule.environments.map((env) => (
|
||||
<EnvironmentLabel
|
||||
key={env.id}
|
||||
size="small"
|
||||
environment={env}
|
||||
userName={env.userName}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
<EnvironmentLabels size="small" environments={schedule.environments} />
|
||||
</Property>
|
||||
<Property label="External ID">
|
||||
{schedule.externalId ? schedule.externalId : "–"}
|
||||
|
||||
+2
-10
@@ -6,7 +6,7 @@ import { typedjson, useTypedLoaderData } from "remix-typedjson";
|
||||
import { BlankstateInstructions } from "~/components/BlankstateInstructions";
|
||||
import { AdminDebugTooltip } from "~/components/admin/debugTooltip";
|
||||
import { InlineCode } from "~/components/code/InlineCode";
|
||||
import { EnvironmentLabel } from "~/components/environments/EnvironmentLabel";
|
||||
import { EnvironmentLabel, EnvironmentLabels } from "~/components/environments/EnvironmentLabel";
|
||||
import { MainCenteredContainer, PageBody, PageContainer } from "~/components/layout/AppLayout";
|
||||
import { LinkButton } from "~/components/primitives/Buttons";
|
||||
import { DateTime } from "~/components/primitives/DateTime";
|
||||
@@ -281,15 +281,7 @@ function SchedulesTable({
|
||||
{schedule.lastRun ? <DateTime date={schedule.lastRun} timeZone="utc" /> : "–"}
|
||||
</TableCell>
|
||||
<TableCell to={path} className={cellClass}>
|
||||
<div className="flex gap-1">
|
||||
{schedule.environments.map((environment) => (
|
||||
<EnvironmentLabel
|
||||
key={environment.id}
|
||||
environment={environment}
|
||||
userName={environment.userName}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
<EnvironmentLabels environments={schedule.environments} size="small" />
|
||||
</TableCell>
|
||||
<TableCell to={path}>
|
||||
<EnabledStatus enabled={schedule.active} />
|
||||
|
||||
-1
@@ -1,5 +1,4 @@
|
||||
import { RuntimeEnvironmentType } from "@trigger.dev/database";
|
||||
import { logger } from "./logger.server";
|
||||
|
||||
const environmentSortOrder: RuntimeEnvironmentType[] = [
|
||||
"DEVELOPMENT",
|
||||
Reference in New Issue
Block a user