This is an automated email from the ASF dual-hosted git repository.
kaxilnaik pushed a commit to branch v3-0-test
in repository https://gitbox.apache.org/repos/asf/airflow.git
The following commit(s) were added to refs/heads/v3-0-test by this push:
new 7c7c86ac917 [v3-0-test] Add keyboard shortcut for fullscreen and wrap
in logs. (#50008) (#50062)
7c7c86ac917 is described below
commit 7c7c86ac9174ab64eb6a94a93da6ffc4c03318cd
Author: github-actions[bot]
<41898282+github-actions[bot]@users.noreply.github.com>
AuthorDate: Thu May 1 16:33:24 2025 +0530
[v3-0-test] Add keyboard shortcut for fullscreen and wrap in logs. (#50008)
(#50062)
* Add keyboard shortcut for fullscreen and wrap in logs.
* Add keyboard shortcut for wrap in log preview and code tab.
* Fix wording as per PR comments.
(cherry picked from commit c2f5cd445793a7d5d4f8e7bb181707c73106129b)
Co-authored-by: Karthikeyan Singaravelan <[email protected]>
---
.../src/airflow/ui/src/pages/Dag/Code/Code.tsx | 18 +++++++++++----
.../ui/src/pages/Dag/Overview/FailedLogs.tsx | 26 +++++++++++++---------
.../ui/src/pages/TaskInstance/Logs/Logs.tsx | 4 ++++
.../src/pages/TaskInstance/Logs/TaskLogHeader.tsx | 23 +++++++++++++------
4 files changed, 50 insertions(+), 21 deletions(-)
diff --git a/airflow-core/src/airflow/ui/src/pages/Dag/Code/Code.tsx
b/airflow-core/src/airflow/ui/src/pages/Dag/Code/Code.tsx
index 60583b43dae..fef86924492 100644
--- a/airflow-core/src/airflow/ui/src/pages/Dag/Code/Code.tsx
+++ b/airflow-core/src/airflow/ui/src/pages/Dag/Code/Code.tsx
@@ -18,6 +18,7 @@
*/
import { Box, Button, Heading, HStack, Link } from "@chakra-ui/react";
import { useState } from "react";
+import { useHotkeys } from "react-hotkeys-hook";
import { useParams } from "react-router-dom";
import { createElement, PrismLight as SyntaxHighlighter } from
"react-syntax-highlighter";
import python from "react-syntax-highlighter/dist/esm/languages/prism/python";
@@ -33,7 +34,7 @@ import type { DAGSourceResponse } from
"openapi/requests/types.gen";
import { DagVersionSelect } from "src/components/DagVersionSelect";
import { ErrorAlert } from "src/components/ErrorAlert";
import Time from "src/components/Time";
-import { ClipboardRoot, ClipboardButton } from "src/components/ui";
+import { ClipboardRoot, ClipboardButton, Tooltip } from "src/components/ui";
import { ProgressBar } from "src/components/ui";
import { useColorMode } from "src/context/colorMode";
import useSelectedVersion from "src/hooks/useSelectedVersion";
@@ -79,6 +80,8 @@ export const Code = () => {
const toggleWrap = () => setWrap(!wrap);
const { colorMode } = useColorMode();
+ useHotkeys("w", toggleWrap);
+
const style = colorMode === "dark" ? oneDark : oneLight;
// wrapLongLines wasn't working with the prsim styles so we have to manually
apply the style
@@ -123,9 +126,16 @@ export const Code = () => {
<ClipboardRoot value={code?.content ?? ""}>
<ClipboardButton />
</ClipboardRoot>
- <Button aria-label={wrap ? "Unwrap" : "Wrap"} bg="bg.panel"
onClick={toggleWrap} variant="outline">
- {wrap ? "Unwrap" : "Wrap"}
- </Button>
+ <Tooltip closeDelay={100} content="Press w to toggle wrap"
openDelay={100}>
+ <Button
+ aria-label={wrap ? "Unwrap" : "Wrap"}
+ bg="bg.panel"
+ onClick={toggleWrap}
+ variant="outline"
+ >
+ {wrap ? "Unwrap" : "Wrap"}
+ </Button>
+ </Tooltip>
</HStack>
</HStack>
{/* We want to show an empty state on 404 instead of an error */}
diff --git a/airflow-core/src/airflow/ui/src/pages/Dag/Overview/FailedLogs.tsx
b/airflow-core/src/airflow/ui/src/pages/Dag/Overview/FailedLogs.tsx
index e3a5d1af6a0..7702e308db2 100644
--- a/airflow-core/src/airflow/ui/src/pages/Dag/Overview/FailedLogs.tsx
+++ b/airflow-core/src/airflow/ui/src/pages/Dag/Overview/FailedLogs.tsx
@@ -18,8 +18,10 @@
*/
import { Flex, Heading, Button } from "@chakra-ui/react";
import { useState } from "react";
+import { useHotkeys } from "react-hotkeys-hook";
import type { TaskInstanceCollectionResponse } from
"openapi/requests/types.gen";
+import { Tooltip } from "src/components/ui";
import { useConfig } from "src/queries/useConfig";
import { TaskLogPreview } from "./TaskLogPreview";
@@ -36,6 +38,8 @@ const FailedLogs = ({
const toggleWrap = () => setWrap(!wrap);
+ useHotkeys("w", toggleWrap);
+
if (taskLogs === undefined || taskLogs.length <= 0) {
return undefined;
}
@@ -44,16 +48,18 @@ const FailedLogs = ({
<Flex flexDirection="column" gap={3}>
<Flex alignItems="center" justifyContent="space-between">
<Heading size="md">Recent Failed Task Logs</Heading>
- <Button
- aria-label={wrap ? "Unwrap" : "Wrap"}
- bg="bg.panel"
- fontSize="sm"
- onClick={toggleWrap}
- size="sm"
- variant="outline"
- >
- {wrap ? "Unwrap" : "Wrap"}
- </Button>
+ <Tooltip closeDelay={100} content="Press w to toggle wrap"
openDelay={100}>
+ <Button
+ aria-label={wrap ? "Unwrap" : "Wrap"}
+ bg="bg.panel"
+ fontSize="sm"
+ onClick={toggleWrap}
+ size="sm"
+ variant="outline"
+ >
+ {wrap ? "Unwrap" : "Wrap"}
+ </Button>
+ </Tooltip>
</Flex>
{taskLogs.map((taskInstance) => (
<TaskLogPreview key={taskInstance.id} taskInstance={taskInstance}
wrap={wrap} />
diff --git a/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/Logs.tsx
b/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/Logs.tsx
index 931caf50d6e..4e2c7af02d1 100644
--- a/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/Logs.tsx
+++ b/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/Logs.tsx
@@ -18,6 +18,7 @@
*/
import { Box, Heading, VStack } from "@chakra-ui/react";
import { useState } from "react";
+import { useHotkeys } from "react-hotkeys-hook";
import { useParams, useSearchParams } from "react-router-dom";
import { useTaskInstanceServiceGetMappedTaskInstance } from "openapi/queries";
@@ -67,6 +68,9 @@ export const Logs = () => {
const toggleWrap = () => setWrap(!wrap);
const toggleFullscreen = () => setFullscreen(!fullscreen);
+ useHotkeys("w", toggleWrap);
+ useHotkeys("f", toggleFullscreen);
+
const onOpenChange = () => {
setFullscreen(false);
};
diff --git
a/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/TaskLogHeader.tsx
b/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/TaskLogHeader.tsx
index 85bfd771f74..a48f2503e02 100644
--- a/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/TaskLogHeader.tsx
+++ b/airflow-core/src/airflow/ui/src/pages/TaskInstance/Logs/TaskLogHeader.tsx
@@ -30,7 +30,7 @@ import { useSearchParams } from "react-router-dom";
import type { TaskInstanceResponse } from "openapi/requests/types.gen";
import { TaskTrySelect } from "src/components/TaskTrySelect";
-import { Button, Select } from "src/components/ui";
+import { Button, Select, Tooltip } from "src/components/ui";
import { SearchParamsKeys } from "src/constants/searchParams";
import { system } from "src/theme";
import { type LogLevel, logLevelColorMapping, logLevelOptions } from
"src/utils/logs";
@@ -179,13 +179,22 @@ export const TaskLogHeader = ({
</Select.Root>
) : undefined}
<HStack>
- <Button aria-label={wrap ? "Unwrap" : "Wrap"} bg="bg.panel"
onClick={toggleWrap} variant="outline">
- {wrap ? "Unwrap" : "Wrap"}
- </Button>
+ <Tooltip closeDelay={100} content="Press w to toggle wrap"
openDelay={100}>
+ <Button
+ aria-label={wrap ? "Unwrap" : "Wrap"}
+ bg="bg.panel"
+ onClick={toggleWrap}
+ variant="outline"
+ >
+ {wrap ? "Unwrap" : "Wrap"}
+ </Button>
+ </Tooltip>
{!isFullscreen && (
- <IconButton aria-label="Full screen" bg="bg.panel"
onClick={toggleFullscreen} variant="outline">
- <MdOutlineOpenInFull />
- </IconButton>
+ <Tooltip closeDelay={100} content="Press f for fullscreen"
openDelay={100}>
+ <IconButton aria-label="Full screen" bg="bg.panel"
onClick={toggleFullscreen} variant="outline">
+ <MdOutlineOpenInFull />
+ </IconButton>
+ </Tooltip>
)}
</HStack>
</HStack>