diff --git a/eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-stage.yml b/eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-stage.yml index 114fef0061..b6a14c54a7 100644 --- a/eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-stage.yml +++ b/eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-stage.yml @@ -68,7 +68,7 @@ stages: operatingSystem: Windows runtime: ${{ runtime }} useManagedSNI: false - vmImage: ADO-MMS22-SQL22 + vmImage: ADO-MMS25-SQL25 - ${{ each runtime in parameters.netTestRuntimes }}: - template: /eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-job.yml@self @@ -81,7 +81,7 @@ stages: operatingSystem: Windows runtime: ${{ runtime }} useManagedSNI: false - vmImage: ADO-MMS22-SQL22 + vmImage: ADO-MMS25-SQL25 - template: /eng/pipelines/ci/managed-instance/sqlclient-ci-managed-instance-job.yml@self parameters: @@ -93,7 +93,7 @@ stages: operatingSystem: Windows runtime: ${{ runtime }} useManagedSNI: true - vmImage: ADO-MMS22-SQL22 + vmImage: ADO-MMS25-SQL25 # ---------------------------------------------------------------------------------------------- # Linux: one job per .NET runtime (managed SNI is always used on non-Windows). @@ -108,4 +108,4 @@ stages: dotnetVerbosity: ${{ parameters.dotnetVerbosity }} operatingSystem: Linux runtime: ${{ runtime }} - vmImage: ADO-UB22-SQL22 + vmImage: ADO-UB24-SQL25 diff --git a/eng/pipelines/ci/stress/sqlclient-ci-stress-stage.yml b/eng/pipelines/ci/stress/sqlclient-ci-stress-stage.yml index 689d1a702b..3cbdb9d31e 100644 --- a/eng/pipelines/ci/stress/sqlclient-ci-stress-stage.yml +++ b/eng/pipelines/ci/stress/sqlclient-ci-stress-stage.yml @@ -89,7 +89,7 @@ stages: template: /eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml@self parameters: saPassword: $(saPassword) - vmImage: ADO-UB22-SQL22 + vmImage: ADO-UB24-SQL25 # ---------------------------------------------------------------------------------------------- # Build and test on Windows @@ -112,7 +112,7 @@ stages: saPassword: $(saPassword) # The Windows images include a suitable .NET Framework runtime, so we don't have to install # one explicitly. - vmImage: ADO-MMS22-SQL22 + vmImage: ADO-MMS25-SQL25 # ---------------------------------------------------------------------------------------------- # Build and test on macOS. diff --git a/eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml b/eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml index 15de459d50..a397108701 100644 --- a/eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml +++ b/eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml @@ -16,8 +16,16 @@ parameters: steps: + # Make sure sqlcmd is available; the SQL Server images do not always ship it. + - template: /eng/pipelines/common/templates/steps/install-sqlcmd-linux-step.yml@self + # Configure SQL Server. - bash: | + if [ -z "${SQLCMD_BIN:-}" ]; then + echo "ERROR: sqlcmd was not resolved by the 'Install sqlcmd [Linux]' step." + exit 1 + fi + sudo systemctl stop mssql-server # Password for the SA user (required) @@ -39,10 +47,11 @@ steps: do echo Waiting for SQL Server to start... sleep 3s - /opt/mssql-tools/bin/sqlcmd \ + "$SQLCMD_BIN" \ -S localhost \ -U SA \ -P "$MSSQL_SA_PW" \ + ${SQLCMD_TRUST_ARG:-} \ -Q "SELECT @@VERSION" 2>/dev/null errstatus=$? ((counter++)) @@ -55,3 +64,6 @@ steps: exit $errstatus fi displayName: 'Configure SQL Server [Linux]' + env: + SQLCMD_BIN: $(SqlCmdBin) + SQLCMD_TRUST_ARG: $(SqlCmdTrustArg) diff --git a/eng/pipelines/common/templates/steps/configure-sql-server-win-step.yml b/eng/pipelines/common/templates/steps/configure-sql-server-win-step.yml index 5659d45de2..6980c1f33c 100644 --- a/eng/pipelines/common/templates/steps/configure-sql-server-win-step.yml +++ b/eng/pipelines/common/templates/steps/configure-sql-server-win-step.yml @@ -5,7 +5,7 @@ ################################################################################# # This step configures an existing SQL Server running on the local Windows host. For example, our -# 1ES Hosted Pool has images like ADO-MMS22-SQL22 that come with SQL Server 2022 pre-installed and +# 1ES Hosted Pool has images like ADO-MMS25-SQL25 that come with SQL Server 2025 pre-installed and # running. parameters: diff --git a/eng/pipelines/common/templates/steps/install-sqlcmd-linux-step.yml b/eng/pipelines/common/templates/steps/install-sqlcmd-linux-step.yml new file mode 100644 index 0000000000..b358f1e446 --- /dev/null +++ b/eng/pipelines/common/templates/steps/install-sqlcmd-linux-step.yml @@ -0,0 +1,82 @@ +################################################################################# +# Licensed to the .NET Foundation under one or more agreements. # +# The .NET Foundation licenses this file to you under the MIT license. # +# See the LICENSE file in the project root for more information. # +################################################################################# + +# Ensures the SQL Server command line tools are available on a Linux agent. +# +# The SQL Server images in our 1ES pool (for example ADO-UB24-SQL25) ship the SQL Server engine but +# do not always ship the command line tools, so install them when they are missing. +# +# Sets two variables for the remaining steps in the job: +# +# SqlCmdBin - absolute path to the sqlcmd executable. +# SqlCmdTrustArg - '-C' when sqlcmd needs to be told to trust the server's self-signed +# certificate, otherwise empty. + +steps: + + - bash: | + set -u + + if ! command -v sudo >/dev/null 2>&1; then + echo "ERROR: 'sudo' is required to install the SQL Server command line tools." + exit 1 + fi + + find_sqlcmd() { + if command -v sqlcmd >/dev/null 2>&1; then + command -v sqlcmd + return 0 + fi + # mssql-tools default install locations. + local candidate + for candidate in /opt/mssql-tools18/bin/sqlcmd /opt/mssql-tools/bin/sqlcmd; do + if [ -x "$candidate" ]; then + echo "$candidate" + return 0 + fi + done + return 1 + } + + if SQLCMD_BIN="$(find_sqlcmd)"; then + echo "Found existing sqlcmd at '$SQLCMD_BIN'." + else + echo "sqlcmd was not found; installing mssql-tools18..." + + # The Microsoft package repository is usually already configured on these images (that is + # where the engine came from), so try a plain install first and only register the repository + # if that fails. + if ! sudo ACCEPT_EULA=Y apt-get install -y mssql-tools18 unixodbc-dev; then + # shellcheck disable=SC1091 + . /etc/os-release + echo "Registering the Microsoft package repository for Ubuntu $VERSION_ID..." + curl -sSL -o /tmp/packages-microsoft-prod.deb \ + "https://packages.microsoft.com/config/ubuntu/$VERSION_ID/packages-microsoft-prod.deb" + sudo dpkg -i /tmp/packages-microsoft-prod.deb + sudo apt-get update + sudo ACCEPT_EULA=Y apt-get install -y mssql-tools18 unixodbc-dev + fi + + if ! SQLCMD_BIN="$(find_sqlcmd)"; then + echo "ERROR: 'sqlcmd' was not found on PATH or in the standard mssql-tools locations," + echo " and installing mssql-tools18 did not provide it." + exit 1 + fi + fi + + # sqlcmd from mssql-tools18 (and go-sqlcmd) encrypts by default, so it needs -C to trust the + # local server's self-signed certificate. The older mssql-tools build does not support -C. + case "$SQLCMD_BIN" in + */mssql-tools/bin/sqlcmd) SQLCMD_TRUST_ARG="" ;; + *) SQLCMD_TRUST_ARG="-C" ;; + esac + + echo "Using sqlcmd '$SQLCMD_BIN' with trust argument '$SQLCMD_TRUST_ARG'." + + # Publish for the remaining steps in this job. + echo "##vso[task.setvariable variable=SqlCmdBin]$SQLCMD_BIN" + echo "##vso[task.setvariable variable=SqlCmdTrustArg]$SQLCMD_TRUST_ARG" + displayName: 'Install sqlcmd [Linux]' diff --git a/eng/pipelines/dotnet-sqlclient-ci-core.yml b/eng/pipelines/dotnet-sqlclient-ci-core.yml index a51bbee3f5..107eb5e6f6 100644 --- a/eng/pipelines/dotnet-sqlclient-ci-core.yml +++ b/eng/pipelines/dotnet-sqlclient-ci-core.yml @@ -308,7 +308,7 @@ stages: testConfigurations: # SQL Server 2016 and 2017 on Windows Server 2022 (x64 only). # x86 testing is intentionally skipped for these legacy SQL versions - # because x86 support is already validated via SQL 2019 and 2022 images. + # because x86 support is already validated via SQL 2019 and 2025 images. ${{ if eq(parameters.runLegacySqlTests, true) }}: # Windows Server 22 with local SQL Server 2016, x64 build platform. windows_sql_16_x64: @@ -416,11 +416,11 @@ stages: SQLRootPath: $(SQL19RootPath) enableLocalDB: true - # Windows Server 22 with local SQL Server 2022, x64 build platform. - windows_sql_22_x64: + # Windows Server 25 with local SQL Server 2025, x64 build platform. + windows_sql_25_x64: pool: ${{parameters.defaultPoolName }} images: - Win22_Sql22: ADO-MMS22-SQL22 + Win25_Sql25: ADO-MMS25-SQL25 TargetFrameworks: ${{parameters.targetFrameworks }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: ${{parameters.buildPlatforms }} @@ -439,14 +439,14 @@ stages: LocalDbAppName: $(LocalDbAppName) LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) AliasName: $(SQLAliasName) - SQLRootPath: $(SQL22RootPath) + SQLRootPath: $(SQL25RootPath) enableLocalDB: true - # Windows Server 22 with local SQL Server 2022, x86 build platform. - windows_sql_22_x86: + # Windows Server 25 with local SQL Server 2025, x86 build platform. + windows_sql_25_x86: pool: ${{parameters.defaultPoolName }} images: - Win22_Sql22_x86: ADO-MMS22-SQL22 + Win25_Sql25_x86: ADO-MMS25-SQL25 TargetFrameworks: [net462, net8.0, net9.0] netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: ${{parameters.buildPlatforms }} @@ -466,14 +466,14 @@ stages: LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) AliasName: $(SQLAliasName) x86TestTargetFrameworks: [net462, net8.0, net9.0] - SQLRootPath: $(SQL22RootPath) + SQLRootPath: $(SQL25RootPath) enableLocalDB: true - # Windows Server 22 with local SQL Server 2022 Named Instance, x64 build platform. - windows_sql_22_named_instance: + # Windows Server 25 with local SQL Server 2025 Named Instance, x64 build platform. + windows_sql_25_named_instance: pool: ${{parameters.defaultPoolName }} images: - Win22_Sql22_Named_Instance: ADO-MMS22-SQL22-WITH-NAMED-INSTANCE + Win25_Sql25_Named_Instance: ADO-MMS25-SQL25-WITH-NAMED-INSTANCE TargetFrameworks: ${{parameters.targetFrameworks }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: ${{parameters.buildPlatforms }} @@ -485,7 +485,7 @@ stages: TCPConnectionString: $(SQL_TCP_INSTANCE_CONN_STRING) NPConnectionString: $(SQL_NP_INSTANCE_CONN_STRING) SupportsIntegratedSecurity: true - SQLRootPath: $(SQL22RootPath) + SQLRootPath: $(SQL25RootPath) instanceName: $(NamedInstance) # Windows Server 2022 and Windows 11, x64 build platform, with Azure SQL Server. @@ -546,12 +546,11 @@ stages: LocalDbAppName: $(LocalDbAppName) LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) - # Linux Ubuntu 20 and 22 with local SQL Server 2022, x64 build platform. - linux_ub20_22_sql_22: + # Linux Ubuntu 24 with local SQL Server 2025, x64 build platform. + linux_ub24_sql_25: pool: ${{parameters.defaultPoolName }} images: - Ubuntu20_Sql22: ADO-UB20-SQL22 - Ubuntu22_Sql22: ADO-UB22-SQL22 + Ubuntu24_Sql25: ADO-UB24-SQL25 TargetFrameworks: ${{parameters.targetFrameworksUnix }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: [AnyCPU] @@ -570,11 +569,11 @@ stages: LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) AliasName: $(SQLAliasName) - # Linux Ubuntu 22 with Azure SQL Server, x64 build platform. + # Linux Ubuntu 24 with Azure SQL Server, x64 build platform. linux_azure_sql: pool: ${{parameters.defaultPoolName }} images: - Ubuntu22_Azure_Sql: ADO-UB22-SQL22 + Ubuntu24_Azure_Sql: ADO-UB24-SQL25 TargetFrameworks: ${{parameters.targetFrameworksUnix }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: [AnyCPU] @@ -597,12 +596,12 @@ stages: LocalDbAppName: $(LocalDbAppName) LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) - # macOS with local SQL Server 2022, x64 build platform. - mac_sql_22: + # macOS with local SQL Server 2025 (docker), x64 build platform. + mac_sql_25: pool: Azure Pipelines hostedPool: true images: - MacOSLatest_Sql22: macos-latest + MacOSLatest_Sql25: macos-latest TargetFrameworks: ${{parameters.targetFrameworksUnix }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: [AnyCPU] @@ -651,11 +650,16 @@ stages: LocalDbAppName: $(LocalDbAppName) LocalDbSharedInstanceName: $(LocalDbSharedInstanceName) - # Linux Ubuntu 22 with remote Enclave-enabled SQL Server 2019, x64 build platform. + # Linux Ubuntu 24 with remote Enclave-enabled SQL Server 2019, x64 build platform. linux_enclave_sql: pool: ADO-CI-AE-1ES-Pool images: - Ubuntu20_Enclave_Sql19: ADO-UB22-Sql22 + # NOTE: This key is also the generated stage name, and is + # referenced by branch policies / required status checks, so it is + # deliberately left unchanged. The 'Sql19' suffix remains + # accurate: these tests target a remote Enclave-enabled SQL Server + # 2019. Only the agent image has moved to Ubuntu 24. + Ubuntu20_Enclave_Sql19: ADO-UB24-SQL25 TargetFrameworks: ${{parameters.targetFrameworksUnix }} netcoreVersionTestUtils: ${{parameters.netcoreVersionTestUtils }} buildPlatforms: [AnyCPU] diff --git a/eng/pipelines/pr/sqlclient-pr-pipeline.yml b/eng/pipelines/pr/sqlclient-pr-pipeline.yml index b72e15ef53..4ab1a31f60 100644 --- a/eng/pipelines/pr/sqlclient-pr-pipeline.yml +++ b/eng/pipelines/pr/sqlclient-pr-pipeline.yml @@ -70,32 +70,32 @@ parameters: default: - displayName: "windows_net462" dotnet: "net462" - image: "ADO-MMS22-SQL22" + image: "ADO-MMS25-SQL25" operatingSystem: "Windows" - displayName: "windows_net8" dotnet: "net8.0" - image: "ADO-MMS22-SQL22" + image: "ADO-MMS25-SQL25" operatingSystem: "Windows" - displayName: "windows_net9" dotnet: "net9.0" - image: "ADO-MMS22-SQL22" + image: "ADO-MMS25-SQL25" operatingSystem: "Windows" - displayName: "windows_net10" dotnet: "net10.0" - image: "ADO-MMS22-SQL22" + image: "ADO-MMS25-SQL25" operatingSystem: "Windows" - displayName: "linux_net8" dotnet: "net8.0" - image: "ADO-UB22-SQL22" + image: "ADO-UB24-SQL25" operatingSystem: "Linux" - displayName: "linux_net9" dotnet: "net9.0" - image: "ADO-UB22-SQL22" + image: "ADO-UB24-SQL25" operatingSystem: "Linux" - displayName: "linux_net10" dotnet: "net10.0" - image: "ADO-UB22-SQL22" + image: "ADO-UB24-SQL25" operatingSystem: "Linux" variables: diff --git a/eng/pipelines/pr/steps/configure-sqlserver-linux-step.yml b/eng/pipelines/pr/steps/configure-sqlserver-linux-step.yml index 8eb8cc40d6..df625dc35e 100644 --- a/eng/pipelines/pr/steps/configure-sqlserver-linux-step.yml +++ b/eng/pipelines/pr/steps/configure-sqlserver-linux-step.yml @@ -5,7 +5,7 @@ ################################################################################# # This step configures an existing SQL Server running on the local Linux host. For example, our 1ES -# Hosted Pool has images like ADO-UB20-SQL22 that come with SQL Server 2022 pre-installed and +# Hosted Pool has images like ADO-UB24-SQL25 that come with SQL Server 2025 pre-installed and # running. parameters: @@ -16,6 +16,9 @@ parameters: steps: + # Make sure sqlcmd is available; the SQL Server images do not always ship it. + - template: /eng/pipelines/common/templates/steps/install-sqlcmd-linux-step.yml@self + # Configure SQL Server. - bash: | set -u @@ -30,15 +33,8 @@ steps: exit 1 fi - SQLCMD_BIN="" - if command -v sqlcmd >/dev/null 2>&1; then - SQLCMD_BIN="$(command -v sqlcmd)" - elif [ -x /opt/mssql-tools18/bin/sqlcmd ]; then - SQLCMD_BIN="/opt/mssql-tools18/bin/sqlcmd" - elif [ -x /opt/mssql-tools/bin/sqlcmd ]; then - SQLCMD_BIN="/opt/mssql-tools/bin/sqlcmd" - else - echo "ERROR: 'sqlcmd' was not found on PATH or in the standard mssql-tools locations." + if [ -z "${SQLCMD_BIN:-}" ]; then + echo "ERROR: sqlcmd was not resolved by the 'Install sqlcmd [Linux]' step." exit 1 fi @@ -79,6 +75,7 @@ steps: -S localhost \ -U SA \ -P "$MSSQL_SA_PW" \ + ${SQLCMD_TRUST_ARG:-} \ -Q "SELECT @@VERSION" 2>/dev/null errstatus=$? ((counter++)) @@ -91,6 +88,9 @@ steps: exit $errstatus fi displayName: 'Configure SQL Server [Linux]' + env: + SQLCMD_BIN: $(SqlCmdBin) + SQLCMD_TRUST_ARG: $(SqlCmdTrustArg) - bash: | set -u @@ -98,15 +98,8 @@ steps: SCRIPT_PATH="$(Build.SourcesDirectory)/tools/testsql/createNorthwindDb.sql" MSSQL_SA_PW="${{ parameters.saPassword }}" - SQLCMD_BIN="" - if command -v sqlcmd >/dev/null 2>&1; then - SQLCMD_BIN="$(command -v sqlcmd)" - elif [ -x /opt/mssql-tools18/bin/sqlcmd ]; then - SQLCMD_BIN="/opt/mssql-tools18/bin/sqlcmd" - elif [ -x /opt/mssql-tools/bin/sqlcmd ]; then - SQLCMD_BIN="/opt/mssql-tools/bin/sqlcmd" - else - echo "ERROR: 'sqlcmd' was not found on PATH or in the standard mssql-tools locations." + if [ -z "${SQLCMD_BIN:-}" ]; then + echo "ERROR: sqlcmd was not resolved by the 'Install sqlcmd [Linux]' step." exit 1 fi @@ -114,6 +107,7 @@ steps: -S localhost \ -U SA \ -P "$MSSQL_SA_PW" \ + ${SQLCMD_TRUST_ARG:-} \ -Q "IF DB_ID(N'Northwind') IS NOT NULL BEGIN ALTER DATABASE [Northwind] SET SINGLE_USER WITH ROLLBACK IMMEDIATE; DROP DATABASE [Northwind]; END" \ -b @@ -121,7 +115,11 @@ steps: -S localhost \ -U SA \ -P "$MSSQL_SA_PW" \ + ${SQLCMD_TRUST_ARG:-} \ -i "$SCRIPT_PATH" \ -b displayName: 'Create Northwind Database [Linux]' retryCountOnTaskFailure: 1 + env: + SQLCMD_BIN: $(SqlCmdBin) + SQLCMD_TRUST_ARG: $(SqlCmdTrustArg) diff --git a/eng/pipelines/pr/steps/configure-sqlserver-windows-step.yml b/eng/pipelines/pr/steps/configure-sqlserver-windows-step.yml index 8e07120b4b..405582d655 100644 --- a/eng/pipelines/pr/steps/configure-sqlserver-windows-step.yml +++ b/eng/pipelines/pr/steps/configure-sqlserver-windows-step.yml @@ -5,7 +5,7 @@ ################################################################################# # This step configures an existing SQL Server running on the local Windows host. For example, our -# 1ES Hosted Pool has images like ADO-MMS22-SQL22 that come with SQL Server 2022 pre-installed and +# 1ES Hosted Pool has images like ADO-MMS25-SQL25 that come with SQL Server 2025 pre-installed and # running. parameters: diff --git a/eng/pipelines/stages/build-azure-package-ci-stage.yml b/eng/pipelines/stages/build-azure-package-ci-stage.yml index b3cf9073d5..7156f9c91f 100644 --- a/eng/pipelines/stages/build-azure-package-ci-stage.yml +++ b/eng/pipelines/stages/build-azure-package-ci-stage.yml @@ -53,8 +53,8 @@ parameters: # # Any pool specified here must contain images with the following names: # - # - ADO-MMS22-SQL22 - # - ADO-UB22-SQL22 + # - ADO-MMS25-SQL25 + # - ADO-UB24-SQL25 # default: $(ci_var_defaultPoolName) @@ -219,7 +219,7 @@ stages: - template: /eng/pipelines/common/templates/steps/configure-sql-server-linux-step.yml@self parameters: saPassword: $(saPassword) - vmImage: ADO-UB22-SQL22 + vmImage: ADO-UB24-SQL25 # ------------------------------------------------------------------------ # Build and test on Windows @@ -277,11 +277,11 @@ stages: # These variables are from an Azure DevOps Library variable # group. fileStreamDirectory: $(FileStreamDirectory) - sqlRootPath: $(SQL22RootPath) - # The ADO-MMS22-SQL22 image includes a local SQL Server that supports + SQLRootPath: $(SQL25RootPath) + # The ADO-MMS25-SQL25 image includes a local SQL Server that supports # integrated security. supportsIntegratedSecurity: true - vmImage: ADO-MMS22-SQL22 + vmImage: ADO-MMS25-SQL25 # ------------------------------------------------------------------------ # Build and test on macOS.