diff --git a/.changeset/famous-files-attend.md b/.changeset/famous-files-attend.md
new file mode 100644
index 000000000..8db7ac93d
--- /dev/null
+++ b/.changeset/famous-files-attend.md
@@ -0,0 +1,5 @@
+---
+'@hyperdx/app': minor
+---
+
+feat: Toggle columns from LogSidePanel
diff --git a/packages/app/src/LogSidePanel.tsx b/packages/app/src/LogSidePanel.tsx
index 3e4bc48ac..1d5dae4c5 100644
--- a/packages/app/src/LogSidePanel.tsx
+++ b/packages/app/src/LogSidePanel.tsx
@@ -482,6 +482,8 @@ function TraceSubpanel({
onPropertyAddClick,
generateChartUrl,
generateSearchUrl,
+ displayedColumns,
+ toggleColumn,
}: {
logData: any;
onClose: () => void;
@@ -493,6 +495,8 @@ function TraceSubpanel({
}) => string;
onPropertyAddClick?: (name: string, value: string) => void;
+ displayedColumns?: string[];
+ toggleColumn?: (column: string) => void;
}) {
const date = new Date(logData.timestamp);
const start = add(date, { minutes: -240 });
@@ -681,6 +685,8 @@ function TraceSubpanel({
generateSearchUrl={generateSearchUrl}
onClose={onClose}
generateChartUrl={generateChartUrl}
+ displayedColumns={displayedColumns}
+ toggleColumn={toggleColumn}
/>
>
@@ -1300,6 +1306,8 @@ function PropertySubpanel({
generateSearchUrl,
onClose,
generateChartUrl,
+ displayedColumns,
+ toggleColumn,
}: {
logData: any;
generateSearchUrl: (query?: string, timeRange?: [Date, Date]) => string;
@@ -1312,6 +1320,8 @@ function PropertySubpanel({
}) => string;
onPropertyAddClick?: (key: string, value: string) => void;
+ displayedColumns?: string[];
+ toggleColumn?: (column: string) => void;
}) {
const [propertySearchValue, setPropertySearchValue] = useState('');
const [isNestedView, setIsNestedView] = useLocalStorage(
@@ -1582,6 +1592,8 @@ function PropertySubpanel({
}}
valueRenderer={(raw, value, ...rawKeyPath) => {
const keyPath = rawKeyPath.slice().reverse();
+ const keyPathString = keyPath.join('.');
+
return (
) : null}
+
+ {!!toggleColumn && keyPath.length === 1 ? (
+
+ ) : null}
+
{
@@ -2032,6 +2062,8 @@ export default function LogSidePanel({
generateChartUrl,
sortKey,
isNestedPanel = false,
+ displayedColumns,
+ toggleColumn,
}: {
logId: string | undefined;
onClose: () => void;
@@ -2048,6 +2080,8 @@ export default function LogSidePanel({
}) => string;
sortKey: string | undefined;
isNestedPanel?: boolean;
+ displayedColumns?: string[];
+ toggleColumn?: (column: string) => void;
}) {
const contextZIndex = useZIndex();
@@ -2222,6 +2256,8 @@ export default function LogSidePanel({
generateSearchUrl={generateSearchUrl}
generateChartUrl={generateChartUrl}
onClose={_onClose}
+ displayedColumns={displayedColumns}
+ toggleColumn={toggleColumn}
/>
) : null}
diff --git a/packages/app/src/LogTable.tsx b/packages/app/src/LogTable.tsx
index 71e2187df..e0aad4eda 100644
--- a/packages/app/src/LogTable.tsx
+++ b/packages/app/src/LogTable.tsx
@@ -784,6 +784,8 @@ export default function LogTable({
onEnd,
onShowPatternsClick,
tableId,
+ displayedColumns,
+ setDisplayedColumns,
}: {
config: {
where: string;
@@ -802,10 +804,11 @@ export default function LogTable({
onEnd?: () => void;
onShowPatternsClick?: () => void;
tableId?: string;
+ displayedColumns: string[];
+ setDisplayedColumns: (columns: string[]) => void;
}) {
const [instructionsOpen, setInstructionsOpen] = useState(false);
const [settingsOpen, setSettingsOpen] = useState(false);
- const [displayedColumns, setDisplayedColumns] = useState([]);
const [wrapLines, setWrapLines] = useState(false);
const prevQueryConfig = usePrevious({ searchedQuery, isLive });
diff --git a/packages/app/src/LogTableWithSidePanel.tsx b/packages/app/src/LogTableWithSidePanel.tsx
index cc5d1f3c4..730ad9097 100644
--- a/packages/app/src/LogTableWithSidePanel.tsx
+++ b/packages/app/src/LogTableWithSidePanel.tsx
@@ -4,6 +4,7 @@ import usePortal from 'react-useportal';
import type { LogView } from './types';
import LogSidePanel from './LogSidePanel';
import LogTable from './LogTable';
+import { useDisplayedColumns } from './useDisplayedColumns';
export function LogTableWithSidePanel({
config,
@@ -82,6 +83,9 @@ export function LogTableWithSidePanel({
const voidFn = useCallback(() => {}, []);
+ const { displayedColumns, setDisplayedColumns, toggleColumn } =
+ useDisplayedColumns();
+
return (
<>
{openedLog != null ? (
@@ -95,6 +99,8 @@ export function LogTableWithSidePanel({
onPropertyAddClick={onPropertyAddClick}
generateSearchUrl={generateSearchUrl}
generateChartUrl={generateChartUrl}
+ displayedColumns={displayedColumns}
+ toggleColumn={toggleColumn}
/>
) : null}
@@ -114,6 +120,8 @@ export function LogTableWithSidePanel({
[setOpenedLog, onRowExpandClick],
)}
onEnd={onSettled}
+ displayedColumns={displayedColumns}
+ setDisplayedColumns={setDisplayedColumns}
/>
>
);
diff --git a/packages/app/src/SearchPage.tsx b/packages/app/src/SearchPage.tsx
index de6efcffc..69ea95049 100644
--- a/packages/app/src/SearchPage.tsx
+++ b/packages/app/src/SearchPage.tsx
@@ -45,6 +45,7 @@ import SearchPageActionBar from './SearchPageActionBar';
import { useTimeQuery } from './timeQuery';
import { MemoPatternTableWithSidePanel } from './PatternTableWithSidePanel';
import { ErrorBoundary } from 'react-error-boundary';
+import { useDisplayedColumns } from './useDisplayedColumns';
const formatDate = (
date: Date,
@@ -323,6 +324,9 @@ const LogViewerContainer = memo(function LogViewerContainer({
[setOpenedLogQuery],
);
+ const { displayedColumns, setDisplayedColumns, toggleColumn } =
+ useDisplayedColumns();
+
return (
<>
>
);
diff --git a/packages/app/src/useDisplayedColumns.ts b/packages/app/src/useDisplayedColumns.ts
new file mode 100644
index 000000000..bf9978b43
--- /dev/null
+++ b/packages/app/src/useDisplayedColumns.ts
@@ -0,0 +1,16 @@
+import { useState } from 'react';
+
+// TODO: Instead of prop drilling additional columns, we can consider using React.Context or Jotai
+export const useDisplayedColumns = () => {
+ const [displayedColumns, setDisplayedColumns] = useState([]);
+
+ const toggleColumn = (column: string) => {
+ if (displayedColumns.includes(column)) {
+ setDisplayedColumns(displayedColumns.filter(c => c !== column));
+ } else {
+ setDisplayedColumns([...displayedColumns, column]);
+ }
+ };
+
+ return { displayedColumns, setDisplayedColumns, toggleColumn };
+};