diff --git a/base/poco/JSON/include/Poco/JSON/ParserImpl.h b/base/poco/JSON/include/Poco/JSON/ParserImpl.h index 7a8ea647180c..6cf2451f5129 100644 --- a/base/poco/JSON/include/Poco/JSON/ParserImpl.h +++ b/base/poco/JSON/include/Poco/JSON/ParserImpl.h @@ -43,6 +43,9 @@ namespace JSON static const std::size_t JSON_PARSE_BUFFER_SIZE = 4096; static const std::size_t JSON_PARSER_STACK_SIZE = 128; static const int JSON_UNLIMITED_DEPTH = -1; + /// Default nesting limit so that parsing untrusted JSON cannot overflow the native stack via + /// Poco's recursive descent. Far above any legitimate JSON; raise per-parser with setDepth. + static const int JSON_DEFAULT_DEPTH = 1000; ParserImpl(const Handler::Ptr & pHandler = new ParseHandler, std::size_t bufSize = JSON_PARSE_BUFFER_SIZE); /// Creates JSON ParserImpl, using the given Handler and buffer size. @@ -109,6 +112,7 @@ namespace JSON struct json_stream * _pJSON; Handler::Ptr _pHandler; int _depth; + int _currentDepth = 0; char _decimalPoint; bool _allowNullByte; bool _allowComments; diff --git a/base/poco/JSON/src/ParserImpl.cpp b/base/poco/JSON/src/ParserImpl.cpp index 07e9f0a256da..b47f5c2430f0 100644 --- a/base/poco/JSON/src/ParserImpl.cpp +++ b/base/poco/JSON/src/ParserImpl.cpp @@ -37,7 +37,7 @@ namespace JSON { ParserImpl::ParserImpl(const Handler::Ptr& pHandler, std::size_t bufSize): _pJSON(new json_stream), _pHandler(pHandler), - _depth(JSON_UNLIMITED_DEPTH), + _depth(JSON_DEFAULT_DEPTH), _decimalPoint('.'), _allowNullByte(true), _allowComments(false) @@ -53,6 +53,7 @@ ParserImpl::~ParserImpl() void ParserImpl::handle(const std::string& json) { + _currentDepth = 0; if (!_allowNullByte && json.find("\\u0000") != json.npos) throw JSONException("Null bytes in strings not allowed."); @@ -139,6 +140,12 @@ void ParserImpl::stripComments(std::string& json) void ParserImpl::handleArray() { + // Enforce the configured depth limit (set via setDepth) to avoid a native-stack + // overflow on deeply nested input. _depth == JSON_UNLIMITED_DEPTH (-1) means no limit. + if (_depth != JSON_UNLIMITED_DEPTH && _currentDepth >= _depth) + throw JSONException("Maximum allowed JSON depth exceeded"); + ++_currentDepth; + json_type tok = json_peek(_pJSON); while (tok != JSON_ARRAY_END && checkError()) { @@ -148,11 +155,17 @@ void ParserImpl::handleArray() if (tok == JSON_ARRAY_END) handle(); else throw JSONException("JSON array end not found"); + + --_currentDepth; } void ParserImpl::handleObject() { + if (_depth != JSON_UNLIMITED_DEPTH && _currentDepth >= _depth) + throw JSONException("Maximum allowed JSON depth exceeded"); + ++_currentDepth; + json_type tok = json_peek(_pJSON); while (tok != JSON_OBJECT_END && checkError()) { @@ -166,6 +179,8 @@ void ParserImpl::handleObject() if (tok == JSON_OBJECT_END) handle(); else throw JSONException("JSON object end not found"); + + --_currentDepth; } diff --git a/base/poco/Net/src/TCPServer.cpp b/base/poco/Net/src/TCPServer.cpp index 98302900bb47..176942a23bf5 100644 --- a/base/poco/Net/src/TCPServer.cpp +++ b/base/poco/Net/src/TCPServer.cpp @@ -153,9 +153,9 @@ void TCPServer::run() } } // Termination request - catch (Poco::InvalidArgumentException&) + catch (Poco::InvalidArgumentException& exc) { - break; + ErrorHandler::logMessage(Message::PRIO_INFORMATION, "Shutting down TCPServer: " + exc.displayText()); } catch (Poco::Exception& exc) { diff --git a/ci/docker/integration/mysql_java_client/Dockerfile b/ci/docker/integration/mysql_java_client/Dockerfile index 373e78bc0584..8f0bcb59f3ec 100644 --- a/ci/docker/integration/mysql_java_client/Dockerfile +++ b/ci/docker/integration/mysql_java_client/Dockerfile @@ -6,10 +6,13 @@ FROM eclipse-temurin:21-jdk-alpine RUN apk --no-cache add curl -# Pin to 8.1.0 (original version): Connector/J 8.2.0+ and 9.x introduce breaking -# changes to the ClickHouse MySQL protocol handshake. CLASSPATH=. is required so -# javac-compiled .class files in the WORKDIR are found at runtime. -ARG ver=8.1.0 +# Connector/J 8.2.0+ (including 9.x) reads the `info` field of the MySQL `OK` +# packet as a length-encoded string; it used to be pinned to 8.1.0 because +# ClickHouse wrote that field as a plain string and newer drivers failed to +# connect. Fixed by length-encoding `info` (see #84542), so test against a +# modern driver. CLASSPATH=. is required so javac-compiled .class files in the +# WORKDIR are found at runtime. +ARG ver=9.7.0 RUN curl -L -o /mysql-connector-j-${ver}.jar https://repo1.maven.org/maven2/com/mysql/mysql-connector-j/${ver}/mysql-connector-j-${ver}.jar ENV CLASSPATH=.:/mysql-connector-j-${ver}.jar diff --git a/cmake/autogenerated_versions.txt b/cmake/autogenerated_versions.txt index 8fa76df59f73..e79ab8206a4b 100644 --- a/cmake/autogenerated_versions.txt +++ b/cmake/autogenerated_versions.txt @@ -2,13 +2,13 @@ # NOTE: VERSION_REVISION has nothing common with DBMS_TCP_PROTOCOL_VERSION, # only DBMS_TCP_PROTOCOL_VERSION should be incremented on protocol changes. -SET(VERSION_REVISION 54520) +SET(VERSION_REVISION 54524) SET(VERSION_MAJOR 26) SET(VERSION_MINOR 3) -SET(VERSION_PATCH 13) -SET(VERSION_GITHASH d23c7536b980c34b39c850b08ef23c509f06aaaa) -SET(VERSION_DESCRIBE v26.3.13.20001.altinityantalya) -SET(VERSION_STRING 26.3.13.20001.altinityantalya) +SET(VERSION_PATCH 17) +SET(VERSION_GITHASH f3c09372ed98d0201254b0b7d1d87e180205801c) +SET(VERSION_DESCRIBE v26.3.17.20001.altinityantalya) +SET(VERSION_STRING 26.3.17.20001.altinityantalya) # end of autochange SET(VERSION_TWEAK 20001) diff --git a/contrib/avro b/contrib/avro index 3b5d52bdf9f9..7b7f6a5bc42e 160000 --- a/contrib/avro +++ b/contrib/avro @@ -1 +1 @@ -Subproject commit 3b5d52bdf9f9f66121b663741f4270b33c91c1a6 +Subproject commit 7b7f6a5bc42e56b6f74de9fc8f52a2a629c53145 diff --git a/contrib/c-ares b/contrib/c-ares index 3ac47ee46edd..c7a3138dcfe3 160000 --- a/contrib/c-ares +++ b/contrib/c-ares @@ -1 +1 @@ -Subproject commit 3ac47ee46edd8ea40370222f91613fc16c434853 +Subproject commit c7a3138dcfe3bb0eaaf10c0c24c36dc66dc790ab diff --git a/contrib/corrosion-cmake/CMakeLists.txt b/contrib/corrosion-cmake/CMakeLists.txt index 5cdf27b47ec0..b32168d64b6b 100644 --- a/contrib/corrosion-cmake/CMakeLists.txt +++ b/contrib/corrosion-cmake/CMakeLists.txt @@ -134,7 +134,10 @@ if (SANITIZE STREQUAL "memory") elseif (SANITIZE STREQUAL "thread") set(RUST_CARGO_BUILD_STD "-Zbuild-std=std,panic_abort,core,alloc") list(APPEND RUSTFLAGS "-Zsanitizer=thread") -elseif (SANITIZE STREQUAL "address") +elseif (SANITIZE STREQUAL "address" OR SANITIZE STREQUAL "address,undefined") + # Rust has no UBSan, so the combined ASan+UBSan build applies only ASan. Besides the + # instrumentation itself, `-Zsanitizer=address` arms wasmtime's `cfg(asan)` guard, preventing + # a stray munmap of live memory at thread exit: https://github.com/bytecodealliance/wasmtime/issues/13857 set(RUST_CARGO_BUILD_STD "-Zbuild-std=std,panic_abort,core,alloc") list(APPEND RUSTFLAGS "-Zsanitizer=address") endif() diff --git a/contrib/curl b/contrib/curl index 8c908d2d0a6d..a05f34973e6c 160000 --- a/contrib/curl +++ b/contrib/curl @@ -1 +1 @@ -Subproject commit 8c908d2d0a6d32abdedda2c52e90bd56ec76c24d +Subproject commit a05f34973e6c4bb629d018f7cb51487be1c904d8 diff --git a/contrib/curl-cmake/CMakeLists.txt b/contrib/curl-cmake/CMakeLists.txt index 90d1659d3d9d..b9c8f955a3d2 100644 --- a/contrib/curl-cmake/CMakeLists.txt +++ b/contrib/curl-cmake/CMakeLists.txt @@ -15,6 +15,7 @@ set (SRCS "${LIBRARY_DIR}/lib/asyn-thrdd.c" "${LIBRARY_DIR}/lib/bufq.c" "${LIBRARY_DIR}/lib/bufref.c" + "${LIBRARY_DIR}/lib/cf-dns.c" "${LIBRARY_DIR}/lib/cf-h1-proxy.c" "${LIBRARY_DIR}/lib/cf-h2-proxy.c" "${LIBRARY_DIR}/lib/cf-haproxy.c" @@ -37,7 +38,6 @@ set (SRCS "${LIBRARY_DIR}/lib/curl_memrchr.c" "${LIBRARY_DIR}/lib/curl_ntlm_core.c" "${LIBRARY_DIR}/lib/curl_range.c" - "${LIBRARY_DIR}/lib/curl_rtmp.c" "${LIBRARY_DIR}/lib/curl_sasl.c" "${LIBRARY_DIR}/lib/curl_sha512_256.c" "${LIBRARY_DIR}/lib/curl_share.c" @@ -47,6 +47,7 @@ set (SRCS "${LIBRARY_DIR}/lib/cw-out.c" "${LIBRARY_DIR}/lib/cw-pause.c" "${LIBRARY_DIR}/lib/dict.c" + "${LIBRARY_DIR}/lib/dnscache.c" "${LIBRARY_DIR}/lib/doh.c" "${LIBRARY_DIR}/lib/dynhds.c" "${LIBRARY_DIR}/lib/easy.c" @@ -100,6 +101,7 @@ set (SRCS "${LIBRARY_DIR}/lib/pingpong.c" "${LIBRARY_DIR}/lib/pop3.c" "${LIBRARY_DIR}/lib/progress.c" + "${LIBRARY_DIR}/lib/protocol.c" "${LIBRARY_DIR}/lib/psl.c" "${LIBRARY_DIR}/lib/rand.c" "${LIBRARY_DIR}/lib/ratelimit.c" @@ -123,6 +125,8 @@ set (SRCS "${LIBRARY_DIR}/lib/system_win32.c" "${LIBRARY_DIR}/lib/telnet.c" "${LIBRARY_DIR}/lib/tftp.c" + "${LIBRARY_DIR}/lib/thrdpool.c" + "${LIBRARY_DIR}/lib/thrdqueue.c" "${LIBRARY_DIR}/lib/transfer.c" "${LIBRARY_DIR}/lib/uint-bset.c" "${LIBRARY_DIR}/lib/uint-hash.c" diff --git a/contrib/curl-cmake/curl_config.h b/contrib/curl-cmake/curl_config.h index 243af6b0a3ae..d36bb558eced 100644 --- a/contrib/curl-cmake/curl_config.h +++ b/contrib/curl-cmake/curl_config.h @@ -57,8 +57,10 @@ #define ENABLE_IPV6 #define USE_OPENSSL -#define USE_THREADS_POSIX +#define HAVE_THREADS_POSIX #define USE_ARES +#define USE_RESOLV_ARES +#define CURL_ENABLE_NTLM #ifdef __illumos__ #define HAVE_POSIX_STRERROR_R 1 diff --git a/contrib/krb5 b/contrib/krb5 index 1279d8ae5acc..857c2d1edd7a 160000 --- a/contrib/krb5 +++ b/contrib/krb5 @@ -1 +1 @@ -Subproject commit 1279d8ae5accd8a7b79ed7f603770fecb90db759 +Subproject commit 857c2d1edd7a4218b84594768587aa53fd63da9e diff --git a/contrib/libarchive b/contrib/libarchive index ded82291ab41..7219b0134d77 160000 --- a/contrib/libarchive +++ b/contrib/libarchive @@ -1 +1 @@ -Subproject commit ded82291ab41d5e355831b96b0e1ff49e24d8939 +Subproject commit 7219b0134d771dc4b51bf86b4d01761b87398b1b diff --git a/contrib/libarchive-cmake/config.h b/contrib/libarchive-cmake/config.h index da7f950da3b7..8b87e9e4d79f 100644 --- a/contrib/libarchive-cmake/config.h +++ b/contrib/libarchive-cmake/config.h @@ -1028,6 +1028,9 @@ typedef uint64_t uintmax_t; /* Define to 1 if you have the header file. */ #define HAVE_STDARG_H 1 +/* Define to 1 if you have the header file. */ +#define HAVE_STDCKDINT_H 1 + /* Define to 1 if you have the header file. */ #define HAVE_STDINT_H 1 diff --git a/contrib/librdkafka b/contrib/librdkafka index cd9a80837602..6aa06cfec6ae 160000 --- a/contrib/librdkafka +++ b/contrib/librdkafka @@ -1 +1 @@ -Subproject commit cd9a80837602fe0f97c146beff752e705f40cb0a +Subproject commit 6aa06cfec6ae35efb6e6f895326ed0ec2ecc2a27 diff --git a/contrib/libxml2 b/contrib/libxml2 index b7fa62cbe8ef..c94eb0210183 160000 --- a/contrib/libxml2 +++ b/contrib/libxml2 @@ -1 +1 @@ -Subproject commit b7fa62cbe8ef0df5869e000d5b690bdedd07f33e +Subproject commit c94eb0210183b9d7cb43f8e7fddc6be55843ef49 diff --git a/contrib/libxml2-cmake/linux_x86_64/include/config.h b/contrib/libxml2-cmake/linux_x86_64/include/config.h index 600e7570e990..8abacf912b82 100644 --- a/contrib/libxml2-cmake/linux_x86_64/include/config.h +++ b/contrib/libxml2-cmake/linux_x86_64/include/config.h @@ -77,7 +77,7 @@ #define PACKAGE_NAME "libxml2" /* Define to the full name and version of this package. */ -#define PACKAGE_STRING "libxml2 2.15.1" +#define PACKAGE_STRING "libxml2 2.15.3" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "libxml2" @@ -86,7 +86,7 @@ #define PACKAGE_URL "" /* Define to the version of this package. */ -#define PACKAGE_VERSION "2.15.1" +#define PACKAGE_VERSION "2.15.3" /* Define to 1 if all of the C90 standard headers exist (not just the ones required in a freestanding environment). This macro is provided for @@ -94,7 +94,7 @@ #define STDC_HEADERS 1 /* Version number of package */ -#define VERSION "2.15.1" +#define VERSION "2.15.3" /* System configuration directory (/etc) */ #define XML_SYSCONFDIR "/usr/local/etc" diff --git a/contrib/libxml2-cmake/linux_x86_64/include/libxml/xmlversion.h b/contrib/libxml2-cmake/linux_x86_64/include/libxml/xmlversion.h index ff8b0ed8011b..e63ad461ce92 100644 --- a/contrib/libxml2-cmake/linux_x86_64/include/libxml/xmlversion.h +++ b/contrib/libxml2-cmake/linux_x86_64/include/libxml/xmlversion.h @@ -16,17 +16,17 @@ /** * the version string like "1.2.3" */ -#define LIBXML_DOTTED_VERSION "2.15.1" +#define LIBXML_DOTTED_VERSION "2.15.3" /** * the version number: 1.2.3 value is 10203 */ -#define LIBXML_VERSION 21501 +#define LIBXML_VERSION 21503 /** * the version number string, 1.2.3 value is "10203" */ -#define LIBXML_VERSION_STRING "21501" +#define LIBXML_VERSION_STRING "21503" /** * extra version information, used to show a git commit description @@ -37,7 +37,7 @@ * Macro to check that the libxml version in use is compatible with * the version the software has been compiled against */ -#define LIBXML_TEST_VERSION xmlCheckVersion(21501); +#define LIBXML_TEST_VERSION xmlCheckVersion(21503); #if 1 /** diff --git a/contrib/mariadb-connector-c b/contrib/mariadb-connector-c index d0a788c5b9fc..95d6264bb43d 160000 --- a/contrib/mariadb-connector-c +++ b/contrib/mariadb-connector-c @@ -1 +1 @@ -Subproject commit d0a788c5b9fcaca2368d9233770d3ca91ea79f88 +Subproject commit 95d6264bb43d31f825cf2f85ce1928557457b62d diff --git a/contrib/mariadb-connector-c-cmake/CMakeLists.txt b/contrib/mariadb-connector-c-cmake/CMakeLists.txt index 58f8a7614cff..93c8469b41b5 100644 --- a/contrib/mariadb-connector-c-cmake/CMakeLists.txt +++ b/contrib/mariadb-connector-c-cmake/CMakeLists.txt @@ -43,6 +43,14 @@ MATH(EXPR MARIADB_VERSION_ID "${MARIADB_CLIENT_VERSION_MAJOR} * 10000 + ${MARIADB_CLIENT_VERSION_MINOR} * 100 + ${MARIADB_CLIENT_VERSION_PATCH}") +set(CPACK_PACKAGE_VERSION_MAJOR 3) +set(CPACK_PACKAGE_VERSION_MINOR 1) +set(CPACK_PACKAGE_VERSION_PATCH 29) +set(CPACK_PACKAGE_VERSION "${CPACK_PACKAGE_VERSION_MAJOR}.${CPACK_PACKAGE_VERSION_MINOR}.${CPACK_PACKAGE_VERSION_PATCH}") +MATH(EXPR MARIADB_PACKAGE_VERSION_ID "${CPACK_PACKAGE_VERSION_MAJOR} * 10000 + + ${CPACK_PACKAGE_VERSION_MINOR} * 100 + + ${CPACK_PACKAGE_VERSION_PATCH}") + IF (NOT MARIADB_PORT) set(MARIADB_PORT 3306) ENDIF () @@ -207,7 +215,7 @@ set(LIBMARIADB_SOURCES ${LIBMARIADB_SOURCES} ${CC_SOURCE_DIR}/plugins/auth/my_auth.c ${CC_SOURCE_DIR}/libmariadb/ma_array.c ${CC_SOURCE_DIR}/libmariadb/ma_charset.c -${CC_SOURCE_DIR}/libmariadb/ma_hash.c +${CC_SOURCE_DIR}/libmariadb/ma_hashtbl.c ${CC_SOURCE_DIR}/libmariadb/ma_net.c ${CC_SOURCE_DIR}/libmariadb/mariadb_charset.c ${CC_SOURCE_DIR}/libmariadb/ma_time.c diff --git a/contrib/orc b/contrib/orc index 1892a6539e65..49e965750a94 160000 --- a/contrib/orc +++ b/contrib/orc @@ -1 +1 @@ -Subproject commit 1892a6539e655280d38a8d0669214dbb9b1d0919 +Subproject commit 49e965750a94627d0ce0a3f3c781423b982cbc1d diff --git a/contrib/postgres b/contrib/postgres index c37596dd61c5..ab6952af3ac8 160000 --- a/contrib/postgres +++ b/contrib/postgres @@ -1 +1 @@ -Subproject commit c37596dd61c5f2b8b7521fdbcdabc651bd9412c4 +Subproject commit ab6952af3ac8cdede654be4dc68f990b0352c213 diff --git a/contrib/postgres-cmake/CMakeLists.txt b/contrib/postgres-cmake/CMakeLists.txt index 88c5eceb1a33..c843d857ba26 100644 --- a/contrib/postgres-cmake/CMakeLists.txt +++ b/contrib/postgres-cmake/CMakeLists.txt @@ -56,6 +56,7 @@ set(SRCS "${POSTGRES_SOURCE_DIR}/src/port/pgstrcasecmp.c" "${POSTGRES_SOURCE_DIR}/src/port/pg_bitutils.c" "${POSTGRES_SOURCE_DIR}/src/port/path.c" + "${POSTGRES_SOURCE_DIR}/src/port/timingsafe_bcmp.c" ) if(NOT OS_DARWIN) diff --git a/contrib/postgres-cmake/pg_config.h b/contrib/postgres-cmake/pg_config.h index 12767588b94d..84e435838d41 100644 --- a/contrib/postgres-cmake/pg_config.h +++ b/contrib/postgres-cmake/pg_config.h @@ -618,19 +618,24 @@ #define PG_MAJORVERSION_NUM 18 /* PostgreSQL minor version number */ -#define PG_MINORVERSION_NUM 3 +#define PG_MINORVERSION_NUM 4 -/* Define to best printf format archetype, usually gnu_printf if available. */ -#define PG_PRINTF_ATTRIBUTE gnu_printf +/* Define to best C++ printf format archetype, usually gnu_printf if + available. */ +#define PG_CXX_PRINTF_ATTRIBUTE gnu_printf + +/* Define to best C printf format archetype, usually gnu_printf if available. + */ +#define PG_C_PRINTF_ATTRIBUTE gnu_printf /* PostgreSQL version as a string */ -#define PG_VERSION "18.3" +#define PG_VERSION "18.4" /* PostgreSQL version as a number */ -#define PG_VERSION_NUM 180003 +#define PG_VERSION_NUM 180004 /* A string containing the version number, platform, and C compiler */ -#define PG_VERSION_STR "PostgreSQL 18.3 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 15.2.1 20250813, 64-bit" +#define PG_VERSION_STR "PostgreSQL 18.4 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 15.2.1 20250813, 64-bit" /* Define to 1 to allow profiling output to be saved separately for each process. */ diff --git a/docker/keeper/Dockerfile.distroless b/docker/keeper/Dockerfile.distroless index 9b422b670f6a..4b30438a93ad 100644 --- a/docker/keeper/Dockerfile.distroless +++ b/docker/keeper/Dockerfile.distroless @@ -146,7 +146,7 @@ RUN mkdir -p \ # Stage 2: Production distroless image. # ────────────────────────────────────────────────────────────────────────────── # Pinned 2026-04-02. Refresh: docker pull gcr.io/distroless/cc-debian13:nonroot && docker inspect --format='{{index .RepoDigests 0}}' gcr.io/distroless/cc-debian13:nonroot -FROM gcr.io/distroless/cc-debian13:nonroot@sha256:8f960b7fc6a5d6e28bb07f982655925d6206678bd9a6cde2ad00ddb5e2077d78 AS production +FROM gcr.io/distroless/cc-debian13:nonroot@sha256:d3cda6e91129130d7229a1806b6a73d292ef245ab032da7851907798024cefba AS production COPY --from=ch-builder /output/ / @@ -169,7 +169,7 @@ ENTRYPOINT ["/usr/bin/clickhouse", "docker-init", "--keeper"] # at /busybox/sh for interactive troubleshooting. # ────────────────────────────────────────────────────────────────────────────── # Pinned 2026-04-02. Refresh: docker pull gcr.io/distroless/cc-debian13:debug-nonroot && docker inspect --format='{{index .RepoDigests 0}}' gcr.io/distroless/cc-debian13:debug-nonroot -FROM gcr.io/distroless/cc-debian13:debug-nonroot@sha256:55dd32378f7562c890342098a04726f4ef386bb86c87bec3db6ed4eef27d99fb AS debug +FROM gcr.io/distroless/cc-debian13:debug-nonroot@sha256:61e8df8909b98d2cf65fa8f620ee8292be40becd9de3b85d42852bee3f86fdb0 AS debug COPY --from=ch-builder /output/ / diff --git a/docker/server/Dockerfile.distroless b/docker/server/Dockerfile.distroless index 77f5f942409b..5db48b755914 100644 --- a/docker/server/Dockerfile.distroless +++ b/docker/server/Dockerfile.distroless @@ -164,7 +164,7 @@ RUN { \ # Stage 2: Production distroless image. # ────────────────────────────────────────────────────────────────────────────── # Pinned 2026-04-02. Refresh: docker pull gcr.io/distroless/cc-debian13:nonroot && docker inspect --format='{{index .RepoDigests 0}}' gcr.io/distroless/cc-debian13:nonroot -FROM gcr.io/distroless/cc-debian13:nonroot@sha256:8f960b7fc6a5d6e28bb07f982655925d6206678bd9a6cde2ad00ddb5e2077d78 AS production +FROM gcr.io/distroless/cc-debian13:nonroot@sha256:d3cda6e91129130d7229a1806b6a73d292ef245ab032da7851907798024cefba AS production COPY --from=ch-builder /output/ / @@ -187,7 +187,7 @@ ENTRYPOINT ["/usr/bin/clickhouse", "docker-init"] # at /busybox/sh for interactive troubleshooting. # ────────────────────────────────────────────────────────────────────────────── # Pinned 2026-04-02. Refresh: docker pull gcr.io/distroless/cc-debian13:debug-nonroot && docker inspect --format='{{index .RepoDigests 0}}' gcr.io/distroless/cc-debian13:debug-nonroot -FROM gcr.io/distroless/cc-debian13:debug-nonroot@sha256:55dd32378f7562c890342098a04726f4ef386bb86c87bec3db6ed4eef27d99fb AS debug +FROM gcr.io/distroless/cc-debian13:debug-nonroot@sha256:61e8df8909b98d2cf65fa8f620ee8292be40becd9de3b85d42852bee3f86fdb0 AS debug COPY --from=ch-builder /output/ / diff --git a/docs/en/sql-reference/data-types/dynamic.md b/docs/en/sql-reference/data-types/dynamic.md index ad6d8d21c6fe..d61a4e55aa1b 100644 --- a/docs/en/sql-reference/data-types/dynamic.md +++ b/docs/en/sql-reference/data-types/dynamic.md @@ -503,6 +503,35 @@ SELECT d, d.Int64 + 1 AS res, toTypeName(res) FROM test; └───────┴──────┴─────────────────┘ ``` +### Type mismatch behavior {#dynamic-type-mismatch-behavior} + +The setting `dynamic_throw_on_type_mismatch` controls what happens when a function is applied to a `Dynamic` column and the actual stored type of a row is incompatible with the function: + +- `true` (default) — throw an exception (`ILLEGAL_TYPE_OF_ARGUMENT`) on the first incompatible row. +- `false` — return `NULL` for incompatible rows and keep the result for compatible rows. + +**Example:** + +```sql +CREATE TABLE test (d Dynamic) ENGINE = Memory; +INSERT INTO test VALUES ('world'), (123), (456); + +-- Default (throw on mismatch): length() does not accept integers, so the query throws. +SELECT length(d) FROM test; -- throws ILLEGAL_TYPE_OF_ARGUMENT + +-- With throw disabled: incompatible rows return NULL. +SET dynamic_throw_on_type_mismatch = false; +SELECT d, length(d) FROM test ORDER BY d::String NULLS LAST; +``` + +```text +┌─d─────┬─length(d)─┐ +│ world │ 5 │ +│ 123 │ ᴺᵁᴸᴸ │ +│ 456 │ ᴺᵁᴸᴸ │ +└───────┴───────────┘ +``` + ## Using Dynamic type in ORDER BY and GROUP BY {#using-dynamic-type-in-order-by-and-group-by} During `ORDER BY` and `GROUP BY` values of `Dynamic` types are compared similar to values of `Variant` type: diff --git a/docs/en/sql-reference/data-types/variant.md b/docs/en/sql-reference/data-types/variant.md index febf9bf05e35..0f97f7f4510c 100644 --- a/docs/en/sql-reference/data-types/variant.md +++ b/docs/en/sql-reference/data-types/variant.md @@ -558,3 +558,32 @@ The result type depends on what the function returns for each variant: TYPE_MISMATCH, CANNOT_CONVERT_TYPE, NO_COMMON_TYPE) are caught and result in NULL for those rows. Other errors like division by zero or out of memory are raised normally to prevent silently hiding real problems. ::: + +### Type mismatch behavior {#variant-type-mismatch-behavior} + +The setting `variant_throw_on_type_mismatch` controls what happens when a function is applied to a `Variant` column and the actual stored type of a row is incompatible with the function: + +- `true` (default) — throw an exception (`ILLEGAL_TYPE_OF_ARGUMENT`) on the first incompatible row. +- `false` — return `NULL` for incompatible rows and keep the result for compatible rows. + +**Example:** + +```sql +CREATE TABLE test (v Variant(String, UInt64)) ENGINE = Memory; +INSERT INTO test VALUES ('hello'), (42), ('foo'); + +-- Default (throw on mismatch): length() does not accept UInt64, so the query throws. +SELECT length(v) FROM test; -- throws ILLEGAL_TYPE_OF_ARGUMENT + +-- With throw disabled: incompatible rows return NULL. +SET variant_throw_on_type_mismatch = false; +SELECT v, length(v) FROM test ORDER BY v::String NULLS LAST; +``` + +```text +┌─v─────┬─length(v)─┐ +│ foo │ 3 │ +│ hello │ 5 │ +│ 42 │ ᴺᵁᴸᴸ │ +└───────┴───────────┘ +``` diff --git a/docs/en/sql-reference/statements/grant.md b/docs/en/sql-reference/statements/grant.md index da84cf6b2d71..703df7dcb3f5 100644 --- a/docs/en/sql-reference/statements/grant.md +++ b/docs/en/sql-reference/statements/grant.md @@ -305,6 +305,7 @@ The hierarchy of privileges in ClickHouse is shown below: - `SYSTEM REDUCE BLOCKING PARTS` - `SYSTEM REPLICATION QUEUES` - `SYSTEM REPLICA READINESS` + - `SYSTEM RESET DDL WORKER` - `SYSTEM RESTART DISK` - `SYSTEM RESTART REPLICA` - `SYSTEM RESTORE REPLICA` diff --git a/programs/server/Server.cpp b/programs/server/Server.cpp index 3fe8dc1e34b4..041ca95163b5 100644 --- a/programs/server/Server.cpp +++ b/programs/server/Server.cpp @@ -1230,7 +1230,8 @@ try // If the startup_console_log_level is set in the config, we override the console logger level. // Specific loggers can still override it. - std::string original_console_log_level_config = config().getString("logger.startup_console_log_level", ""); + bool console_log_level_was_set = config().has("logger.console_log_level"); + std::string original_console_log_level_config = config().getString("logger.console_log_level", ""); bool should_restore_console_log_level = false; if (config().has("logger.startup_console_log_level") && !config().getString("logger.startup_console_log_level").empty()) { @@ -3114,9 +3115,20 @@ try if (should_restore_console_log_level) { - config().setString("logger.console_log_level", original_console_log_level_config); - Loggers::updateLevels(config(), logger()); - LOG_INFO(log, "Restored console logger level to {}", original_console_log_level_config); + /// If the level was unset just remove the override so the default can be set via + /// Loggers::updateLevels again; otherwise restore the configured value. + if (console_log_level_was_set) + { + config().setString("logger.console_log_level", original_console_log_level_config); + Loggers::updateLevels(config(), logger()); + LOG_INFO(log, "Restored console logger level to {}", original_console_log_level_config); + } + else + { + config().remove("logger.console_log_level"); + Loggers::updateLevels(config(), logger()); + LOG_INFO(log, "Restored console logger level to logger.level"); + } } for (auto & server : servers) diff --git a/programs/server/dashboard.html b/programs/server/dashboard.html index d371512145e6..6fbd34913fb7 100644 --- a/programs/server/dashboard.html +++ b/programs/server/dashboard.html @@ -264,7 +264,7 @@ filter: contrast(125%); } - #add, #reload, #edit, #search { + #add, #add-metrics, #reload, #edit, #search { padding: 0.25rem 0.5rem; text-align: center; font-weight: bold; @@ -279,7 +279,7 @@ height: 3ex; } - #add:hover, #reload:hover, #edit:hover, #search:hover { + #add:hover, #add-metrics:hover, #reload:hover, #edit:hover, #search:hover { background: var(--button-background-color); } @@ -441,6 +441,34 @@ color: var(--global-error-color); } + #metrics-editor { + display: none; + grid-template-columns: auto fit-content(10%) fit-content(10%); + grid-template-rows: auto fit-content(10%); + row-gap: 1rem; + column-gap: 1rem; + } + + #metrics-editor-textarea { + width: 100%; + height: 100%; + grid-row: 1; + grid-column: 1 / span 3; + } + + #metrics-editor input[type="submit"] { + padding: 0.5rem; + } + + #metrics-editor input[type="submit"]:disabled { + opacity: 0.5; + cursor: default; + } + + #metrics-editor-message { + color: var(--text-color); + } + #charts > div:only-child .display-only-if-more-than-one-chart { display: none; } @@ -475,6 +503,7 @@
🌚🌞 + @@ -490,6 +519,12 @@
+
+ +   + + +