本文目录导读:

在 PHP 中管理版本号通常涉及以下几个层面,我会从简单到复杂逐一说明:
基础版本号获取
当前 PHP 版本
// 获取完整版本号 echo PHP_VERSION; // 输出: 8.2.12 echo phpversion(); // 功能相同 // 获取主要版本号 echo PHP_MAJOR_VERSION; // 输出: 8 echo PHP_MINOR_VERSION; // 输出: 2 echo PHP_RELEASE_VERSION; // 输出: 12
版本比较
// 版本号比较(支持语义化版本)
if (version_compare(PHP_VERSION, '7.4.0', '>=')) {
echo "PHP 版本 >= 7.4.0";
}
// 检查是否支持特定特性
if (version_compare(PHP_VERSION, '8.0.0', '>=')) {
// PHP 8 特有的写法
}
应用自身版本管理
常量定义方式
class App {
const VERSION = '1.2.3';
const BUILD = '20231212';
public static function getVersion() {
return self::VERSION . '-' . self::BUILD;
}
}
// 使用
echo App::getVersion(); // 输出: 1.2.3-20231212
Composer 方式(推荐)
在 composer.json 中定义版本:
{
"name": "my/project",
"version": "1.0.0"
}
同时在 PHP 中读取:
// 自动加载后读取
$composer = json_decode(file_get_contents('../composer.json'), true);
echo $composer['version'];
语义化版本管理(SemVer)
完整实现类
class VersionManager {
private $major;
private $minor;
private $patch;
private $preRelease; // alpha, beta, rc
private $buildMeta; // 构建元数据
public function __construct($version = '1.0.0') {
$this->parse($version);
}
private function parse($version) {
// 正则解析语义化版本
preg_match('/^(\d+)\.(\d+)\.(\d+)(?:-([0-9A-Za-z.-]+))?(?:\+([0-9A-Za-z.-]+))?$/',
$version, $matches);
if (count($matches) >= 4) {
$this->major = (int)$matches[1];
$this->minor = (int)$matches[2];
$this->patch = (int)$matches[3];
$this->preRelease = $matches[4] ?? null;
$this->buildMeta = $matches[5] ?? null;
} else {
throw new InvalidArgumentException("无效版本号: $version");
}
}
// 版本号递增
public function bumpMajor() {
$this->major++;
$this->minor = 0;
$this->patch = 0;
$this->preRelease = null;
return $this;
}
public function bumpMinor() {
$this->minor++;
$this->patch = 0;
$this->preRelease = null;
return $this;
}
public function bumpPatch() {
$this->patch++;
$this->preRelease = null;
return $this;
}
// 转换为字符串
public function toString() {
$version = "{$this->major}.{$this->minor}.{$this->patch}";
if ($this->preRelease) {
$version .= "-{$this->preRelease}";
}
if ($this->buildMeta) {
$version .= "+{$this->buildMeta}";
}
return $version;
}
// 比较版本
public function compareTo(VersionManager $other) {
return version_compare($this->toString(), $other->toString());
}
}
// 使用示例
$version = new VersionManager('1.2.3');
$version->bumpMinor();
echo $version->toString(); // 输出: 1.3.0
$v1 = new VersionManager('2.0.0-alpha');
$v2 = new VersionManager('2.0.0');
echo $v1->compareTo($v2); // -1 (v1 < v2)
数据库版本管理
记录版本在数据库中
class DatabaseVersionManager {
private $db;
private $versionTable;
public function __construct(PDO $db, $versionTable = 'schema_migrations') {
$this->db = $db;
$this->versionTable = $versionTable;
$this->createVersionTable();
}
private function createVersionTable() {
$this->db->exec("
CREATE TABLE IF NOT EXISTS {$this->versionTable} (
version VARCHAR(20) PRIMARY KEY,
applied_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)
");
}
public function getCurrentVersion() {
$stmt = $this->db->query("SELECT MAX(version) FROM {$this->versionTable}");
return $stmt->fetchColumn() ?: '0.0.0';
}
public function migrateTo($targetVersion) {
$currentVersion = $this->getCurrentVersion();
// 获取迁移文件列表
$migrations = $this->getMigrationFiles();
foreach ($migrations as $file) {
$version = pathinfo($file, PATHINFO_FILENAME);
if (version_compare($version, $currentVersion, '>') &&
version_compare($version, $targetVersion, '<=')) {
$this->runMigration($file);
$this->recordVersion($version);
echo "已执行迁移: $version\n";
}
}
}
private function runMigration($file) {
// 执行迁移文件
$sql = file_get_contents($file);
$this->db->exec($sql);
}
private function recordVersion($version) {
$stmt = $this->db->prepare(
"INSERT INTO {$this->versionTable} (version) VALUES (?)"
);
$stmt->execute([$version]);
}
private function getMigrationFiles() {
$migrationDir = __DIR__ . '/migrations';
return glob($migrationDir . '/*.sql');
}
}
API 版本控制
REST API 版本管理
class ApiVersionManager {
private $supportedVersions = ['v1', 'v2', 'v3'];
private $defaultVersion = 'v1';
public function detectVersion() {
// 从请求头获取
$header = $_SERVER['HTTP_ACCEPT'] ?? '';
if (preg_match('/application\/vnd\.myapi\.(v\d+)\+json/', $header, $matches)) {
return $this->validateVersion($matches[1]);
}
// 从 URL 获取
$path = $_SERVER['REQUEST_URI'] ?? '';
if (preg_match('/\/api\/(v\d+)\//', $path, $matches)) {
return $this->validateVersion($matches[1]);
}
return $this->defaultVersion;
}
private function validateVersion($version) {
if (in_array($version, $this->supportedVersions)) {
return $version;
}
throw new HttpException(400, "不支持的 API 版本: $version");
}
public function routeToVersion($routes) {
$version = $this->detectVersion();
if (!isset($routes[$version])) {
throw new HttpException(404, "版本 $version 不存在");
}
return $routes[$version];
}
}
配置文件方式
config/version.php
return [
'version' => '1.0.0',
'build' => '20231212.1430',
'released_at' => '2023-12-12 14:30:00',
'php_minimum' => '7.4.0',
'dependencies' => [
'laravel/framework' => '^8.0',
'guzzlehttp/guzzle' => '^7.0'
],
'environment' => [
'min_php_extensions' => ['pdo', 'mbstring', 'curl'],
]
];
class Application {
private $config;
public function __construct() {
$this->config = include('config/version.php');
$this->checkEnvironment();
}
private function checkEnvironment() {
if (version_compare(PHP_VERSION, $this->config['php_minimum'], '<')) {
throw new RuntimeException(
"需要 PHP {$this->config['php_minimum']} 或更高版本,当前是 " . PHP_VERSION
);
}
foreach ($this->config['environment']['min_php_extensions'] as $extension) {
if (!extension_loaded($extension)) {
throw new RuntimeException("缺少 PHP 扩展: $extension");
}
}
}
public function getVersion() {
return [
'version' => $this->config['version'],
'environment' => PHP_VERSION
];
}
}
最佳实践建议
- 使用语义化版本 (SemVer):始终保持
MAJOR.MINOR.PATCH格式 - 自动化版本管理:使用 Composer 或环境变量
- 版本日志:维护 CHANGELOG.md
- 兼容性检测:上线前检查环境版本
- API 版本策略:URL 路径或 Accept Header
- 数据库迁移:记录每次 schema 变更版本
这些方法可以根据项目需求组合使用,对于大型应用,建议使用 Composer 管理依赖版本,并结合 Git tag 管理发布版本。