1+ import { XMarkIcon } from "@heroicons/react/20/solid" ;
12import { type LoaderFunctionArgs } from "@remix-run/node" ;
3+ import { Form } from "@remix-run/react" ;
24import type { TaskTriggerSource } from "@trigger.dev/database" ;
3- import { useCallback , useEffect , useMemo , useRef , useState } from "react" ;
5+ import { type ReactNode , useCallback , useEffect , useMemo , useRef , useState } from "react" ;
46import ReactGridLayout from "react-grid-layout" ;
57import { typedjson , useTypedLoaderData } from "remix-typedjson" ;
68import { z } from "zod" ;
@@ -15,7 +17,8 @@ import { QueuesFilter } from "~/components/metrics/QueuesFilter";
1517import { ScopeFilter } from "~/components/metrics/ScopeFilter" ;
1618import { TitleWidget } from "~/components/metrics/TitleWidget" ;
1719import { CreateDashboardPageButton } from "~/components/navigation/DashboardDialogs" ;
18- import { NavBar , PageAccessories , PageTitle } from "~/components/primitives/PageHeader" ;
20+ import { Button } from "~/components/primitives/Buttons" ;
21+ import { NavBar , PageTitle } from "~/components/primitives/PageHeader" ;
1922import { TimeFilter } from "~/components/runs/v3/SharedFilters" ;
2023import { $replica } from "~/db.server" ;
2124import { useEnvironment } from "~/hooks/useEnvironment" ;
@@ -146,13 +149,6 @@ export default function Page() {
146149 < PageContainer >
147150 < NavBar >
148151 < PageTitle title = { title } />
149- < PageAccessories >
150- < CreateDashboardPageButton
151- organization = { organization }
152- project = { project }
153- environment = { environment }
154- />
155- </ PageAccessories >
156152 </ NavBar >
157153 < PageBody scrollable = { false } >
158154 < div className = "h-full" >
@@ -168,6 +164,14 @@ export default function Page() {
168164 possiblePrompts = { possiblePrompts }
169165 possibleOperations = { possibleOperations }
170166 possibleProviders = { possibleProviders }
167+ filterAccessories = {
168+ < CreateDashboardPageButton
169+ organization = { organization }
170+ project = { project }
171+ environment = { environment }
172+ shortcut = { { key : "n" } }
173+ />
174+ }
171175 />
172176 </ div >
173177 </ PageBody >
@@ -191,6 +195,7 @@ export function MetricDashboard({
191195 onRenameWidget,
192196 onDeleteWidget,
193197 onDuplicateWidget,
198+ filterAccessories,
194199} : {
195200 /** The layout items (positions/sizes) - fully controlled from parent */
196201 layout : LayoutItem [ ] ;
@@ -215,6 +220,7 @@ export function MetricDashboard({
215220 onRenameWidget ?: ( widgetId : string , newTitle : string ) => void ;
216221 onDeleteWidget ?: ( widgetId : string ) => void ;
217222 onDuplicateWidget ?: ( widgetId : string , widget : WidgetData ) => void ;
223+ filterAccessories ?: ReactNode ;
218224} ) {
219225 const { value, values } = useSearchParams ( ) ;
220226 const { width, containerRef, mounted } = useContainerWidth ( ) ;
@@ -242,6 +248,13 @@ export function MetricDashboard({
242248 const providers = values ( "providers" ) . filter ( ( v ) => v !== "" ) ;
243249
244250 const activeFilters = filterConfig ?? [ "tasks" , "queues" ] ;
251+ const hasAppliedFilters =
252+ tasks . length > 0 ||
253+ queues . length > 0 ||
254+ models . length > 0 ||
255+ prompts . length > 0 ||
256+ operations . length > 0 ||
257+ providers . length > 0 ;
245258
246259 const handleLayoutChange = useCallback (
247260 ( newLayout : readonly LayoutItem [ ] ) => {
@@ -266,31 +279,42 @@ export function MetricDashboard({
266279
267280 return (
268281 < div className = "grid max-h-full grid-rows-[auto_1fr] overflow-hidden" >
269- < div className = "flex items-center gap-1 border-b border-b-grid-bright py-2 pl-2 pr-3" >
270- < ScopeFilter />
271- { activeFilters . includes ( "tasks" ) && (
272- < LogsTaskFilter possibleTasks = { possibleTasks ?? [ ] } />
273- ) }
274- { activeFilters . includes ( "queues" ) && < QueuesFilter /> }
275- { activeFilters . includes ( "models" ) && (
276- < ModelsFilter possibleModels = { possibleModels ?? [ ] } />
277- ) }
278- { activeFilters . includes ( "prompts" ) && (
279- < PromptsFilter possiblePrompts = { possiblePrompts ?? [ ] } />
280- ) }
281- { activeFilters . includes ( "operations" ) && (
282- < OperationsFilter possibleOperations = { possibleOperations ?? [ ] } />
283- ) }
284- { activeFilters . includes ( "providers" ) && (
285- < ProvidersFilter possibleProviders = { possibleProviders ?? [ ] } />
282+ < div className = "flex items-center justify-between gap-x-2 border-b border-b-grid-bright py-2 pl-2 pr-3" >
283+ < div className = "flex flex-wrap items-center gap-x-1.5 gap-y-1" >
284+ < ScopeFilter shortcut = { { key : "s" } } />
285+ { activeFilters . includes ( "tasks" ) && (
286+ < LogsTaskFilter possibleTasks = { possibleTasks ?? [ ] } />
287+ ) }
288+ { activeFilters . includes ( "queues" ) && < QueuesFilter /> }
289+ { activeFilters . includes ( "models" ) && (
290+ < ModelsFilter possibleModels = { possibleModels ?? [ ] } />
291+ ) }
292+ { activeFilters . includes ( "prompts" ) && (
293+ < PromptsFilter possiblePrompts = { possiblePrompts ?? [ ] } />
294+ ) }
295+ { activeFilters . includes ( "operations" ) && (
296+ < OperationsFilter possibleOperations = { possibleOperations ?? [ ] } />
297+ ) }
298+ { activeFilters . includes ( "providers" ) && (
299+ < ProvidersFilter possibleProviders = { possibleProviders ?? [ ] } />
300+ ) }
301+ < TimeFilter
302+ defaultPeriod = { defaultPeriod }
303+ labelName = "Period"
304+ hideLabel
305+ maxPeriodDays = { maxPeriodDays }
306+ valueClassName = "text-text-bright"
307+ shortcut = { { key : "d" } }
308+ />
309+ { hasAppliedFilters && (
310+ < Form className = "-ml-1 h-6" >
311+ < Button variant = "minimal/small" LeadingIcon = { XMarkIcon } tooltip = "Clear all filters" />
312+ </ Form >
313+ ) }
314+ </ div >
315+ { filterAccessories && (
316+ < div className = "flex shrink-0 items-center" > { filterAccessories } </ div >
286317 ) }
287- < TimeFilter
288- defaultPeriod = { defaultPeriod }
289- labelName = "Period"
290- hideLabel
291- maxPeriodDays = { maxPeriodDays }
292- valueClassName = "text-text-bright"
293- />
294318 </ div >
295319 < div
296320 ref = { containerRef }
0 commit comments