Upgradujte PHP ovladače pro SQL Server

Upgradujte SQLSRV a PDO_SQLSRV společně, aby obě rozšíření používala stejnou rodinu vydání. PHP ovladače používají Microsoft ODBC ovladač pro SQL Server, proto si před upgradem zkontrolujte systémové požadavky.

Aktualizace mění nativní kód načítaný do PHP procesů. Smíšené nasazení může pokračovat v běhu předchozí verze, selhat při spuštění PHP nebo používat různé verze ovladačů pro CLI a webovou aplikaci. Inventarizujte každý PHP runtime a uchovejte předchozí soubory a konfiguraci, dokud ověření neskončí.

Vyberte cestu upgradu

Současná instalace Instalace cílového systému Procedure
Koláčový graf PIE Spusť PIE se stejným spustitelným souborem PHP nebo explicitně php-config, pak ověř každý SAPI
Windows uvolněný ZIP ZIP vytvořený ve Windows Nahraďte obě verzované knihovny DLL a aktualizujte obě konfigurační položky společně
Vydaný soubor ZIP pro Windows PIE Nainstalujte oba balíčky PIE, nahraďte verzované položky DLL položkami PIE a odstraňte duplicity
Archiv pro Linux nebo macOS PIE Nainstalujte oba balíčky PIE, nahraďte položky archive-filename hodnotami sqlsrv.so a pdo_sqlsrv.so a zachovejte pořadí načítání PDO
Linux nebo macOS PIE Nová minor verze PHP Nainstalujte nové vývojové nástroje pro PHP, vytvořte obě rozšíření pro danou instalaci PHP a nakonfigurujte každé SAPI zvlášť

Nepřepisujte předchozí binárky, dokud nemáte záložní kopii pro obnovení. Neupgradujte jen jedno rozšíření, když aplikace používá obě API.

Před upgradem

  1. Poznamenejte si spustitelný soubor PHP, konfigurační soubor, architekturu, režim bezpečnosti vláken a aktuální verze ovladačů.

    php --version
    php --ini
    php --ri sqlsrv
    php --ri pdo_sqlsrv
    
  2. Zálohujte soubor php.ini a všechny soubory specifické pro rozšíření .ini, které načítají sqlsrv nebo pdo_sqlsrv.

  3. Zkontrolujte matici kompatibility pro cílovou verzi PHP a cílový operační systém.

  4. Zkontrolujte tabulku kompatibility ODBC v Systémových požadavcích. Nainstalujte podporovanou verzi ODBC před nebo během aktualizace PHP ovladače, pokud to vyžaduje cílové vydání ovladače.

  5. Naplánujte restart každého procesu, který načítá PHP, včetně webového serveru, PHP FastCGI Process Manager (PHP-FPM), pracovníků fronty a dlouhodobě běžících pracovníků příkazového řádku.

  6. Zaznamenejte základní hodnotu z každého runtime:

    • ExtensionVer zobrazené pomocí php --ri sqlsrv a php --ri pdo_sqlsrv.
    • Byl načten konfigurační soubor a prohledán adresář .ini.
    • Adresář rozšíření a názvy aktivních ovladačů.
    • Jde o úspěšný smoke test aplikace, který využívá každé API, na kterém vaše aplikace závisí.
  7. Připravte rollback:

    • Pokud změníte vedlejší verzi PHP, nechte si k dispozici předchozí runtime PHP. Zaznamenejte spustitelný soubor nakonfigurovaný pro každý webový server a worker.
    • Uchovejte kopie předchozích SQLSRV a PDO_SQLSRV souborů.
    • Uchovávájte kopie všech php.ini změněných nebo specifických .ini souborů pro rozšíření.
    • Pokud aktualizace změní verzi balíčku ODBC, zaznamenejte předchozí verzi balíčku ODBC.
    • Definovat, jak zastavit provoz nebo přerušit práci pracovníků, zatímco jsou nativní soubory rozšíření nahrazeny.

Upgradujte na Windows s PIE

Použijte PHP Installer for Extensions (PIE) s PHP spustitelným souborem, který aplikaci provozuje. Nejprve si stáhněte a ověřte PIE. Před spuštěním kteréhokoli instalačního příkazu odveďte aplikační provoz a zastavte webový server, procesy FastCGI a pracovníky, kteří používají tuto instalaci PHP. Zabránit automatickému restartu, dokud nejsou připravena obě rozšíření i jejich konfigurace. Udržujte samostatnou příkazovou relaci pro PIE.

Dočasně zakomentujte stávající položky rozšíření SQLSRV a PDO_SQLSRV v konfiguraci CLI používané nástrojem PIE. Jinak může PHP proces běžící PIE udržet staré DLL načtené a zabránit jejich nahrazení. Nechte si zapnutá požadovaná rozšíření PIE.

Z adresáře obsahujícího pie.phar, nainstalujte oba balíčky zvlášť:

php .\pie.phar install microsoft/sqlsrv
php .\pie.phar install microsoft/pdo_sqlsrv

PIE instalovat php_sqlsrv.dll a php_pdo_sqlsrv.dll. V každé aktivní konfiguraci nahraďte verzované ZIP položky jako extension=php_sqlsrv_85_ts_x64.dll a extension=php_pdo_sqlsrv_85_ts_x64.dll za:

extension=php_sqlsrv.dll
extension=php_pdo_sqlsrv.dll

Povolte oba záznamy a odstraňte duplicitní záznamy SQLSRV a PDO_SQLSRV, i když PIE hlásí, že automatické povolení bylo úspěšné. Pokud webový server používá jinou PHP instalaci, zopakujte aktualizaci a změny konfigurace pro tuto instalaci.

Restartujte každý proces PHP, poté spusťte php --ri sqlsrv a php --ri pdo_sqlsrv pomocí příslušného spustitelného souboru. Potvrďte, že ExtensionVer uvádí cílovou verzi pro oba ovladače. U webové aplikace omezte přístup k diagnostické stránce před vytvořením dočasné phpinfo() stránky. Ověřte obě hodnoty a pak stránku smažte.

Aktualizujte instalaci ZIP ve Windows

  1. Stáhněte si Windows ZIP cílové verze ze stránky Microsoft Drivers for PHP for SQL Server releases.

  2. Ověřte, že názvy nových dynamických linkových knihoven (DLL) odpovídají vedlejší verzi PHP, architektuře a režimu bezpečnosti vláken. Před nahrazením souborů zastavte PHP webový server nebo pracovní procesy.

  3. Nahraďte oba soubory php_sqlsrv_*.dll a php_pdo_sqlsrv_*.dll v adresáři rozšíření PHP. Pokud se názvy souborů stále shodují, ponechte si stávající extension= záznamy. Jinak je aktualizujte společně.

  4. Nainstalujte nebo upgradujte ovladač Microsoft ODBC pro SQL Server, pokud cílový PHP ovladač vyžaduje novší podporovanou verzi.

  5. Restartujte všechny procesy PHP, které používají nahrazené knihovny DLL. Běžící proces udržuje staré nativní rozšíření načtené až do jeho ukončení.

Upgradujte na Linux nebo macOS s PIE

  1. Pokud PIE není nainstalován, postupujte podle instalace a předpokladů platformy pro PIE. Ověřte, že jsou nainstalovány PHP vývojové nástroje a ODBC vývojový balíček. V interaktivní relaci může PIE vyzvat instalaci chybějících build nástrojů prostřednictvím správce balíčků platformy. V neinteraktivní relaci je nainstalujte před spuštěním PIE.

  2. Před upgradem vyberte instalaci PHP. Při instalaci s určenou verzí přidejte možnost PIE --with-php-config do obou instalačních příkazů. Například použijte pie install --with-php-config=/usr/bin/php-config8.4 microsoft/sqlsrv , když zamýšlený konfigurační nástroj je /usr/bin/php-config8.4. Stejnou možnost aplikujte na microsoft/pdo_sqlsrv. Pro verzované spustitelné soubory Alpine použijte instalační příkazy Alpine.

  3. Odvést provoz aplikace a zastavit webový server, procesy PHP-FPM a pracovníky, kteří používají tuto instalaci PHP. Zabraňte automatickému restartu, dokud nejsou připravena obě rozšíření i jejich konfigurace. Pro PIE používejte samostatnou relaci příkazového řádku.

    Dočasně zakomentujte stávající SQLSRV a PDO_SQLSRV rozšířené položky v konfiguraci CLI používané PIE. Nechte si zapnutá požadovaná rozšíření PIE.

  4. Aktualizujte oba balíčky zvlášť. Tyto příkazy používají výchozí instalaci PHP nástroje PIE:

    pie install microsoft/sqlsrv
    pie install microsoft/pdo_sqlsrv
    
  5. Zkontrolujte každou aktivní konfiguraci instalace PHP používané vaší aplikací. Pokud předchozí ruční instalace používala archivní názvy souborů jako extension=SQLSRV_8.4_NTS.so a extension=PDO_SQLSRV_8.4_NTS.so, nahraďte tyto položky jmény souborů instalovanými PIE:

    extension=sqlsrv.so
    extension=pdo_sqlsrv.so
    

    Znovu povolte oba záznamy ovladačů a odstraňte duplicity. Mějte PDO_SQLSRV v prohledávaném konfiguračním souboru, který se načítá po PDO, jak je popsáno v Načtení ovladačů v Linuxu a macOS. Tuto změnu konfigurace opakujte pro příkazovou řádku, PHP-FPM, webový server a konfigurace workerů, které vaše aplikace používá.

  6. Aktualizujte ovladač Microsoft ODBC pro SQL Server, když to vyžaduje cílové vydání.

  7. Restartujte všechny služby CLI workeru, queue workeru, webového serveru a PHP-FPM, které používají aktualizovanou instalaci PHP.

Restartujte a ověřte

Nahrazení souboru rozšíření neaktualizuje proces PHP, který už načetl starý binární soubor. Před ověřením aktualizace restartujte webový server, PHP-FPM a všechny dlouhodobě fungující PHP pracovníky.

  1. Ověřte runtime příkazového řádku:

    php --ri sqlsrv
    php --ri pdo_sqlsrv
    php -m | findstr /I "sqlsrv pdo_sqlsrv"
    

    Na Linuxu nebo macOS nahraďte poslední příkaz za php -m | grep -E 'sqlsrv|pdo_sqlsrv'.

  2. U webové aplikace omezte přístup k diagnostické stránce před vytvořením dočasné phpinfo() stránky. Ověřte načtený konfigurační soubor, adresář rozšíření a ExtensionVer pro oba ovladače. Potvrďte, že to ExtensionVer hlásí cílovou verzi, a pak stránku odstraňte.

  3. Spusť existující aplikační smoke test, který prověří jak SQLSRV, tak PDO_SQLSRV, pokud vaše aplikace používá obojí. Během této kontroly nechte konfiguraci připojení beze změny, aby upgrade test netestoval i nesouvisející změnu připojení.

Pokud se ovladač nenačte, porovnejte minoritní verzi PHP, architekturu, režim bezpečnosti vláken, adresář rozšíření a instalaci ODBC s hodnotami zaznamenanými před upgradem.

Ověřte obě API i obě verze

Uložte tento program jako verify-driver-upgrade.php:

<?php
$results = [
    'SQLSRV' => [
        'loaded' => extension_loaded('sqlsrv') && function_exists('sqlsrv_connect'),
        'version' => phpversion('sqlsrv'),
    ],
    'PDO_SQLSRV' => [
        'loaded' => extension_loaded('pdo_sqlsrv')
            && in_array('sqlsrv', PDO::getAvailableDrivers(), true),
        'version' => phpversion('pdo_sqlsrv'),
    ],
];

$failed = false;
foreach ($results as $name => $result) {
    $version = $result['version'] === false ? 'unknown' : $result['version'];
    echo "$name: " . ($result['loaded'] ? 'loaded' : 'missing') . ", version $version" . PHP_EOL;
    $failed = $failed || !$result['loaded'] || $result['version'] === false;
}

exit($failed ? 1 : 0);

Spusť program pomocí spustitelného souboru CLI a dočasně v každém webovém runtime. Ověřte, že obě nahlášené verze odpovídají vydání, které jste nainstalovali. Po ověření webovou kopii odstraňte.

Tento program ověřuje vrstvu rozšíření PHP. Poté spusťte beze změny aplikační smoke test, abyste ověřili načítání ODBC, možnosti připojení, autentizaci, přístup do databáze, vrácené typy PHP a chování při čištění.

Ověřte chování databáze před a po upgradu

Používejte stejný program a nastavení připojení před i po upgradu. Ponechání testu beze změny odděluje změny ovladačů od změn v aplikaci nebo konfiguraci připojení.

Nastavte proměnné prostředí SQL_SERVER_NAME, SQL_DATABASE, SQL_UID a SQL_PWD pro testovací účet odpovídáním na výzvy. Zadejte surové hodnoty bez uvozovek shellu nebo kódování ovladače. Nezahrňujte přihlašovací údaje do příkazové řádky ani do nahrané terminálové relace.

Ve Windows PowerShell zadejte název serveru a název databáze, poté použijte dialogové okno pro zadání přihlašovacích údajů nebo výzvu pro testovací účet:

$env:SQL_SERVER_NAME = Read-Host "Server name (tcp:<server>,1433)"
$env:SQL_DATABASE = Read-Host "Database name"
$credential = Get-Credential -Message "Enter the database test account"
if ($null -eq $credential) {
    throw "Database test credentials are required."
}
$env:SQL_UID = $credential.UserName
$env:SQL_PWD = $credential.GetNetworkCredential().Password
Remove-Variable credential

Na Linuxu nebo macOS používejte Bash. Před čtením jakýchkoli hodnot deaktivujte sledování příkazů. Výzva k zadání hesla nezobrazuje zadané znaky:

set +x
IFS= read -r -p 'Server name (tcp:<server>,1433): ' SQL_SERVER_NAME
IFS= read -r -p 'Database name: ' SQL_DATABASE
IFS= read -r -p 'User name: ' SQL_UID
IFS= read -r -s -p 'Password: ' SQL_PWD
printf '\n'
export SQL_SERVER_NAME SQL_DATABASE SQL_UID SQL_PWD

Prostředí obsahuje heslo v otevřeném textu, aby ho PHP mohl číst. Tyto proměnné používejte pouze v testovací relaci, netiskněte je a po testování je vymažte.

Uložte tento program jako test-driver-upgrade.php. Ponechte hodnoty prostředí beze změny. Program zdvojí zavírací závorky a přidává vnější závorky před předáním názvu databáze, uživatelského jména a hesla ovladači. Toto kódování zachovává literální složené závorky a zabraňuje tomu, aby středníky oddělovaly možnosti připojení.

<?php
$serverName = getenv('SQL_SERVER_NAME');
$database = getenv('SQL_DATABASE');
$uid = getenv('SQL_UID');
$pwd = getenv('SQL_PWD');

if ($serverName === false || $serverName === ''
    || $database === false || $database === ''
    || $uid === false || $uid === ''
    || $pwd === false || $pwd === '') {
    fwrite(STDERR, "Set SQL_SERVER_NAME, SQL_DATABASE, SQL_UID, and SQL_PWD." . PHP_EOL);
    exit(1);
}

$database = '{' . str_replace('}', '}}', $database) . '}';
$uid = '{' . str_replace('}', '}}', $uid) . '}';
$pwd = '{' . str_replace('}', '}}', $pwd) . '}';

$connectionOptions = [
    "Database" => $database,
    "UID" => $uid,
    "PWD" => $pwd,
    "Encrypt" => 1,
    "TrustServerCertificate" => 0,
];

$sqlsrvConnection = sqlsrv_connect($serverName, $connectionOptions);
if ($sqlsrvConnection === false) {
    foreach (sqlsrv_errors() as $error) {
        fwrite(
            STDERR,
            "SQLSRV {$error['SQLSTATE']} ({$error['code']}): {$error['message']}" . PHP_EOL
        );
    }
    exit(1);
}

$sqlsrvStatement = sqlsrv_query($sqlsrvConnection, "SELECT 1 AS TEST_VALUE");
if ($sqlsrvStatement === false) {
    foreach (sqlsrv_errors() as $error) {
        fwrite(
            STDERR,
            "SQLSRV {$error['SQLSTATE']} ({$error['code']}): {$error['message']}" . PHP_EOL
        );
    }
    sqlsrv_close($sqlsrvConnection);
    exit(1);
}

$sqlsrvRow = sqlsrv_fetch_array($sqlsrvStatement, SQLSRV_FETCH_ASSOC);
if ($sqlsrvRow === false || $sqlsrvRow === null || (int) $sqlsrvRow['TEST_VALUE'] !== 1) {
    fwrite(STDERR, "SQLSRV returned an unexpected result." . PHP_EOL);
    sqlsrv_free_stmt($sqlsrvStatement);
    sqlsrv_close($sqlsrvConnection);
    exit(1);
}

echo "SQLSRV query: 1" . PHP_EOL;
sqlsrv_free_stmt($sqlsrvStatement);
sqlsrv_close($sqlsrvConnection);

$failed = false;
try {
    $pdoConnection = new PDO(
        "sqlsrv:server=$serverName;Database=$database;Encrypt=1;TrustServerCertificate=0",
        $uid,
        $pwd,
        [PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION]
    );
    $pdoStatement = $pdoConnection->query("SELECT 1 AS TEST_VALUE");
    $pdoRow = $pdoStatement->fetch(PDO::FETCH_ASSOC);
    if ($pdoRow === false || (int) $pdoRow['TEST_VALUE'] !== 1) {
        throw new RuntimeException("PDO_SQLSRV returned an unexpected result.");
    }

    echo "PDO_SQLSRV query: 1" . PHP_EOL;
} catch (Throwable $exception) {
    fwrite(STDERR, $exception->getMessage() . PHP_EOL);
    $failed = true;
} finally {
    unset($pdoStatement);
    unset($pdoConnection);
}

exit($failed ? 1 : 0);

Spusť program před upgradem a ulož výstup z úspěšného spuštění. Spusť nezměněný soubor znovu po restartu všech PHP procesů:

php test-driver-upgrade.php

Obě spuštění by měla vytvořit:

SQLSRV query: 1
PDO_SQLSRV query: 1

Pokud se spuštění po upgradu nezdaří, zachovejte přesný SQLSTATE nebo výjimku. Poté porovnejte selhání se základnou, verzemi rozšíření, aktivní konfigurací, verzí ODBC a stavem restartu procesu. Vraťte zpět obě PHP rozšíření najednou, když nemůžete v rámci okna nasazení opravit nesoulad.

Po ověření smažte testovací soubor a vymažte dočasné proměnné prostředí. V PowerShellu spusťte:

Remove-Item .\verify-driver-upgrade.php, .\test-driver-upgrade.php
Remove-Item Env:\SQL_SERVER_NAME, Env:\SQL_DATABASE, Env:\SQL_UID, Env:\SQL_PWD

V Linuxu nebo macOS spusťte:

rm verify-driver-upgrade.php test-driver-upgrade.php
unset SQL_SERVER_NAME SQL_DATABASE SQL_UID SQL_PWD

Vrátit zpět neúspěšnou aktualizaci

  1. Zastavte postižené webové servery, PHP-FPM pooly a dlouho běžící workery.

  2. Pokud jste změnili vedlejší verzi PHP, obnovte předchozí runtime PHP a nasměrujte každý webový server a worker zpět na tu instalaci.

  3. Obnovte oba předchozí soubory ovladačů. Obnovte předchozí položky SQLSRV a PDO_SQLSRV konfigurace společně.

  4. Obnovte předchozí balíček ODBC pouze tehdy, pokud novější verze způsobila selhání a starší balíček zůstává podporován verzí ovladače PHP, kterou jste obnovili.

  5. Restartujte procesy a znovu spusťte základní verzní kontroly a smoke testy aplikace.

  6. Uchovávejte logy neúspěšných upgradů a přesnou chybu spuštění PHP nebo chybu připojení. Pomáhají určit, zda selhání souvisí s načítáním PHP, načítačem operačního systému, ODBC nebo připojením k databázi.

Řešení potíží s upgradem

Symptom Pravděpodobná příčina Nápravná akce
PIE je úspěšné, ale ExtensionVer zůstává nezměněné Starý verzovaný záznam stále načítá předchozí soubor Nahraďte starý záznam, odstraňte duplikáty a restartujte všechny PHP procesy
SQLSRV a PDO_SQLSRV hlásí různé verze Bylo vyměněno pouze jedno rozšíření nebo jeden SAPI má zastaralou konfiguraci Aktualizujte a konfigurujte obě rozšíření současně v každém prostředí běhu
CLI hlásí cílovou verzi, ale web ne Web SAPI používá jinou instalaci PHP nebo nebyla restartována Porovnejte konfigurační adresáře a adresáře rozšíření a pak restartujte správný proces
PHP startup hlásí chybu architektury nebo symbolu Rozšíření neodpovídá PHP buildu Obnovte předchozí soubory, poté znovu sestavte nebo vyberte soubory pro správnou minor verzi PHP, architekturu a režim bezpečnosti vláken
Rozšíření se načítají, ale připojení selhává po změně ODBC Konfigurace ODBC, chování certifikátu, autentizace nebo síťový přístup se změnily Zachyťte SQLSTATE a chybu nativního ovladače před rollbackem nebo změnou nastavení připojení
Procesy workeru selhávají, zatímco nové webové požadavky jsou úspěšné Dlouhodobě běžící workery stále drží předchozí rozšíření nebo konfiguraci Odstavit a restartovat každý worker proces