From aad1a4eaecb95da6763a5461cb0b41b544271a06 Mon Sep 17 00:00:00 2001 From: Pierre Jeambrun Date: Tue, 29 Jul 2025 16:51:59 +0200 Subject: [PATCH 1/2] Revert "Fix editing connection with sensitive extra field (#52403)" This reverts commit 8ef792dafef6e64faf5daa376bfa5238b1c14c87. --- .../core_api/datamodels/connections.py | 25 +++++- .../src/pages/Connections/ConnectionForm.tsx | 12 +-- .../ui/src/queries/useEditConnection.tsx | 4 +- .../routes/public/test_connections.py | 81 ++++++++++++++++--- 4 files changed, 96 insertions(+), 26 deletions(-) diff --git a/airflow-core/src/airflow/api_fastapi/core_api/datamodels/connections.py b/airflow-core/src/airflow/api_fastapi/core_api/datamodels/connections.py index f2ac1f7a9403a..2a6bd6bec8af2 100644 --- a/airflow-core/src/airflow/api_fastapi/core_api/datamodels/connections.py +++ b/airflow-core/src/airflow/api_fastapi/core_api/datamodels/connections.py @@ -17,12 +17,15 @@ from __future__ import annotations +import json from collections import abc from typing import Annotated -from pydantic import Field +from pydantic import Field, field_validator +from pydantic_core.core_schema import ValidationInfo from airflow.api_fastapi.core_api.base import BaseModel, StrictBaseModel +from airflow.sdk.execution_time.secrets_masker import redact # Response Models @@ -39,6 +42,26 @@ class ConnectionResponse(BaseModel): password: str | None extra: str | None + @field_validator("password", mode="after") + @classmethod + def redact_password(cls, v: str | None, field_info: ValidationInfo) -> str | None: + if v is None: + return None + return str(redact(v, field_info.field_name)) + + @field_validator("extra", mode="before") + @classmethod + def redact_extra(cls, v: str | None) -> str | None: + if v is None: + return None + try: + extra_dict = json.loads(v) + redacted_dict = redact(extra_dict) + return json.dumps(redacted_dict) + except json.JSONDecodeError: + # we can't redact fields in an unstructured `extra` + return v + class ConnectionCollectionResponse(BaseModel): """Connection Collection serializer for responses.""" diff --git a/airflow-core/src/airflow/ui/src/pages/Connections/ConnectionForm.tsx b/airflow-core/src/airflow/ui/src/pages/Connections/ConnectionForm.tsx index 9e4e38647eaf4..bf921a1de3c99 100644 --- a/airflow-core/src/airflow/ui/src/pages/Connections/ConnectionForm.tsx +++ b/airflow-core/src/airflow/ui/src/pages/Connections/ConnectionForm.tsx @@ -57,7 +57,7 @@ const ConnectionForm = ({ const { conf: extra, setConf } = useParamStore(); const { control, - formState: { isDirty, isValid }, + formState: { isValid }, handleSubmit, reset, watch, @@ -94,14 +94,6 @@ const ConnectionForm = ({ mutateConnection(data); }; - const hasChanges = () => { - if (isDirty) { - return true; - } - - return JSON.stringify(JSON.parse(extra)) !== JSON.stringify(JSON.parse(initialConnection.extra)); - }; - const validateAndPrettifyJson = (value: string) => { try { const parsedJson = JSON.parse(value) as JSON; @@ -242,7 +234,7 @@ const ConnectionForm = ({