diff --git a/airflow/www/static/js/api/useGridData.test.ts b/airflow/www/static/js/api/useGridData.test.ts index 929303efe1f5d..3e83e29ee56a2 100644 --- a/airflow/www/static/js/api/useGridData.test.ts +++ b/airflow/www/static/js/api/useGridData.test.ts @@ -34,7 +34,6 @@ const commonDagRunParams = { lastSchedulingDecision: null, externalTrigger: false, conf: null, - confIsJson: false, note: "", }; diff --git a/airflow/www/static/js/components/RenderedJsonField.tsx b/airflow/www/static/js/components/RenderedJsonField.tsx new file mode 100644 index 0000000000000..518f6b9fd82df --- /dev/null +++ b/airflow/www/static/js/components/RenderedJsonField.tsx @@ -0,0 +1,70 @@ +/*! + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +import React from "react"; + +import ReactJson from "react-json-view"; + +import { Flex, Button, Code, Spacer, useClipboard } from "@chakra-ui/react"; + +interface Props { + content: string; +} + +const JsonParse = (content: string) => { + let contentJson = null; + let contentFormatted = ""; + let isJson = false; + try { + contentJson = JSON.parse(content); + contentFormatted = JSON.stringify(contentJson, null, 4); + isJson = true; + } catch (e) { + // skip + } + return [isJson, contentJson, contentFormatted]; +}; + +const RenderedJsonField = ({ content }: Props) => { + const [isJson, contentJson, contentFormatted] = JsonParse(content); + const { onCopy, hasCopied } = useClipboard(contentFormatted); + + return isJson ? ( + + + + + + ) : ( + {content} + ); +}; + +export default RenderedJsonField; diff --git a/airflow/www/static/js/dag/details/dagRun/Details.tsx b/airflow/www/static/js/dag/details/dagRun/Details.tsx index c769da72d5c4f..317cbd99f2a32 100644 --- a/airflow/www/static/js/dag/details/dagRun/Details.tsx +++ b/airflow/www/static/js/dag/details/dagRun/Details.tsx @@ -16,21 +16,8 @@ * specific language governing permissions and limitations * under the License. */ -import React, { useEffect } from "react"; -import { - Flex, - Box, - Button, - Spacer, - Table, - Tbody, - Tr, - Td, - useClipboard, - Text, -} from "@chakra-ui/react"; - -import ReactJson from "react-json-view"; +import React from "react"; +import { Flex, Box, Table, Tbody, Tr, Td, Text } from "@chakra-ui/react"; import type { DagRun as DagRunType } from "src/types"; import { SimpleStatus } from "src/dag/StatusBox"; @@ -38,25 +25,13 @@ import { ClipboardText } from "src/components/Clipboard"; import { formatDuration, getDuration } from "src/datetime_utils"; import Time from "src/components/Time"; import RunTypeIcon from "src/components/RunTypeIcon"; +import RenderedJsonField from "src/components/RenderedJsonField"; interface Props { run: DagRunType; } -const formatConf = (conf: string | null | undefined): string => { - if (!conf) { - return ""; - } - return JSON.stringify(JSON.parse(conf), null, 4); -}; - const DagRunDetails = ({ run }: Props) => { - const { onCopy, setValue, hasCopied } = useClipboard(formatConf(run?.conf)); - - useEffect(() => { - setValue(formatConf(run?.conf)); - }, [run, setValue]); - if (!run) return null; const { state, @@ -69,7 +44,6 @@ const DagRunDetails = ({ run }: Props) => { queuedAt, externalTrigger, conf, - confIsJson, } = run; return ( @@ -161,28 +135,9 @@ const DagRunDetails = ({ run }: Props) => { Run config - {confIsJson ? ( - - - - - - - - ) : ( - {conf ?? "None"} - )} + + + diff --git a/airflow/www/static/js/dag/details/taskInstance/Details.tsx b/airflow/www/static/js/dag/details/taskInstance/Details.tsx index 7432db840494b..dfd2a921d35df 100644 --- a/airflow/www/static/js/dag/details/taskInstance/Details.tsx +++ b/airflow/www/static/js/dag/details/taskInstance/Details.tsx @@ -33,6 +33,7 @@ import type { TaskInstance as GridTaskInstance, TaskState, } from "src/types"; +import RenderedJsonField from "src/components/RenderedJsonField"; import TrySelector from "./TrySelector"; interface Props { @@ -319,7 +320,7 @@ const Details = ({ gridInstance, taskInstance, group }: Props) => { Rendered Templates - +
{Object.keys(instance.renderedFields).map((key) => { const renderedFields = instance.renderedFields as Record< @@ -339,7 +340,7 @@ const Details = ({ gridInstance, taskInstance, group }: Props) => { ); diff --git a/airflow/www/static/js/dag/grid/dagRuns/index.test.tsx b/airflow/www/static/js/dag/grid/dagRuns/index.test.tsx index a02df41975569..ebbb1f86e0cb4 100644 --- a/airflow/www/static/js/dag/grid/dagRuns/index.test.tsx +++ b/airflow/www/static/js/dag/grid/dagRuns/index.test.tsx @@ -43,7 +43,6 @@ const generateRuns = (length: number): DagRun[] => executionDate: datestring, externalTrigger: false, conf: null, - confIsJson: false, note: "someRandomValue", })); @@ -64,7 +63,6 @@ describe("Test DagRuns", () => { lastSchedulingDecision: datestring, externalTrigger: false, conf: null, - confIsJson: false, note: "someRandomValue", }, { @@ -80,7 +78,6 @@ describe("Test DagRuns", () => { lastSchedulingDecision: datestring, externalTrigger: false, conf: null, - confIsJson: false, note: "someRandomValue", }, ]; diff --git a/airflow/www/static/js/dag/grid/index.test.tsx b/airflow/www/static/js/dag/grid/index.test.tsx index f307fabedf158..ece090f7c890f 100644 --- a/airflow/www/static/js/dag/grid/index.test.tsx +++ b/airflow/www/static/js/dag/grid/index.test.tsx @@ -153,7 +153,6 @@ const mockGridData = { note: "myCoolDagRun", externalTrigger: false, conf: null, - confIsJson: false, }, ], ordering: ["dataIntervalStart"], diff --git a/airflow/www/static/js/types/index.ts b/airflow/www/static/js/types/index.ts index 573072b5ffada..1984a92c9e843 100644 --- a/airflow/www/static/js/types/index.ts +++ b/airflow/www/static/js/types/index.ts @@ -65,7 +65,6 @@ interface DagRun { lastSchedulingDecision: string | null; externalTrigger: boolean; conf: string | null; - confIsJson: boolean; note: string | null; } diff --git a/airflow/www/static/js/utils/index.test.ts b/airflow/www/static/js/utils/index.test.ts index 5d9c05cbb824c..aba3312bfb2e2 100644 --- a/airflow/www/static/js/utils/index.test.ts +++ b/airflow/www/static/js/utils/index.test.ts @@ -139,7 +139,6 @@ describe("Test getDagRunLabel", () => { lastSchedulingDecision: "2021-11-08T21:14:19.704433+00:00", externalTrigger: false, conf: null, - confIsJson: false, note: "someRandomValue", } as DagRun;
{key} - {field as string} +