PHP 專案中常需根據作業系統調整行為 (如路徑分隔符、指令執行、相容性處理)。獲取 OS 類型分為兩種截然不同場景:伺服器端 (PHP 執行環境) 與 客戶端 (瀏覽器/用戶裝置)。本文詳解兩種場景的標準做法、陷阱與最佳實踐。
PHP 在編譯/啟動時即確定執行環境 OS,提供極高效能的存取方式:
PHP_OS 常量 (推薦)"Linux", "WINNT", "Darwin", "FreeBSD"。"WINNT" (含 Vista/7/10/11),非 "Windows"。判斷邏輯建議用 strtoupper(substr(PHP_OS, 0, 3)) === 'WIN'。php_uname('s') 函數's' 回傳作業系統名稱 (同 PHP_OS)。'n' (主機名), 'r' (釋出版本), 'v' (版本資訊), 'm' (機器類型), 'a' (全部)。| OS 家族 | 典型 PHP_OS / php_uname('s') 值 |
|---|---|
| Windows (所有版本) | WINNT, WIN32 |
| Linux (各發行版) | Linux |
| macOS | Darwin |
| FreeBSD | FreeBSD |
| OpenBSD | OpenBSD |
| NetBSD | NetBSD |
| SunOS / Solaris | SunOS |
| AIX | AIX |
| HP-UX | HP-UX |
| Cygwin | CYGWIN_NT-x.x |
class OS {
public static function isWindows(): bool {
return strtoupper(substr(PHP_OS, 0, 3)) === 'WIN';
}
public static function isLinux(): bool {
return PHP_OS === 'Linux';
}
public static function isMac(): bool {
return PHP_OS === 'Darwin';
}
public static function getPathSeparator(): string {
return self::isWindows() ? '\\' : '/';
}
public static function getCommandPrefix(): string {
return self::isWindows() ? 'cmd /c ' : '';
}
}
// 使用範例
$logPath = __DIR__ . OS::getPathSeparator() . 'logs';
$cmd = OS::getCommandPrefix() . 'php artisan schedule:run';
客戶端 OS 資訊包含在 HTTP 請求 Header User-Agent 中。核心挑戰:UA 字串極其龐雜、可偽造、格式無標準、移動裝置碎片化嚴重。
原文提供的函數使用已棄用的 eregi() (PHP 7 移除),且邏輯僅覆蓋極少數桌面 OS,完全無法識別 Android, iOS, Windows Phone, 平板, 智慧電視, 爬蟲, 物聯網裝置。程式碼已過時,僅供理解原理參考。
請勿手寫正則解析 UA。使用 Composer 引入業界標準庫:
| 庫 (Packagist) | 特點 | 安裝命令 |
|---|---|---|
| jenssegers/agent | Laravel 官方推薦,基於 ua-parser/uap-php,API 友善,支援裝置/瀏覽器/機器人/平台完整偵測 | composer require jenssegers/agent |
| ua-parser/uap-php | 核心解析引擎,使用官方 regexes.yaml 規則庫,定期更新,精準度最高 | composer require ua-parser/uap-php |
| donatj/useragent | 零依賴、輕量、純 PHP,適合不想引入 Symfony/Laravel 依賴的專案 | composer require donatj/useragent |
// jenssegers/agent (推薦)
use Jenssegers\Agent\Agent;
$agent = new Agent();
$agent->setUserAgent($_SERVER['HTTP_USER_AGENT'] ?? '');
if ($agent->isDesktop()) {
$os = $agent->platform(); // Windows, macOS, Linux, Ubuntu, Chrome OS...
} elseif ($agent->isMobile()) {
$os = $agent->platform(); // Android, iOS, BlackBerry...
} elseif ($agent->isTablet()) {
$os = $agent->platform(); // iPadOS, Android...
} elseif ($agent->isRobot()) {
$os = 'Bot: ' . $agent->robot();
}
// 獲取完整資訊
$browser = $agent->browser(); // Chrome, Firefox, Safari...
$version = $agent->version($browser);
$device = $agent->device(); // iPhone, iPad, Samsung Galaxy...
$lang = $agent->languages(); // ['zh-TW', 'en-US', ...]
PHP_OS / php_uname()。$_SERVER['HTTP_USER_AGENT']。navigator.userAgentData (User-Agent Client Hints API),後端僅作備援。Sec-CH-UA-* Header。伺服器端 OS 偵測用 PHP_OS (高效、可靠);客戶端 OS 偵測**棄用手寫正則**,引入 jenssegers/agent 等標準庫,並認清 UA 可偽造、隱私敏感、標準演進的現實。正確分離兩種場景,是構建健壯跨平台 PHP 應用的關鍵。