短链接是 API 站点常见工具接口。下面代码使用 SQLite 存储,包含创建短链和访问跳转两个接口,单文件可运行。
<?php
declare(strict_types=1);
$baseUrl = 'http://127.0.0.1:8000';
$pdo = new PDO('sqlite:' . __DIR__ . '/shortlink.sqlite');
$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$pdo->exec('CREATE TABLE IF NOT EXISTS links (
code TEXT PRIMARY KEY,
url TEXT NOT NULL,
created_at TEXT NOT NULL,
clicks INTEGER NOT NULL DEFAULT 0
)');
function response(int $code, string $message, $data = null, int $status = 200): void
{
http_response_code($status);
header('Content-Type: application/json; charset=utf-8');
echo json_encode(compact('code', 'message', 'data'), JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
exit;
}
function input(): array
{
$data = json_decode(file_get_contents('php://input') ?: '{}', true);
return is_array($data) ? $data : [];
}
function code(int $length = 6): string
{
$chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
$value = '';
for ($i = 0; $i < $length; $i++) {
$value .= $chars[random_int(0, strlen($chars) - 1)];
}
return $value;
}
$method = $_SERVER['REQUEST_METHOD'] ?? 'GET';
$path = trim(parse_url($_SERVER['REQUEST_URI'] ?? '/', PHP_URL_PATH), '/');
if ($method === 'POST' && $path === 'api/short-links') {
$data = input();
$url = trim((string)($data['url'] ?? ''));
if (!filter_var($url, FILTER_VALIDATE_URL)) {
response(422, 'url 格式错误', null, 422);
}
do {
$shortCode = code();
$exists = $pdo->prepare('SELECT code FROM links WHERE code = ?');
$exists->execute([$shortCode]);
} while ($exists->fetchColumn());
$stmt = $pdo->prepare('INSERT INTO links(code, url, created_at) VALUES (?, ?, ?)');
$stmt->execute([$shortCode, $url, date('Y-m-d H:i:s')]);
response(0, '创建成功', [
'code' => $shortCode,
'short_url' => rtrim($baseUrl, '/') . '/' . $shortCode,
'url' => $url,
], 201);
}
if ($method === 'GET' && preg_match('/^[a-zA-Z0-9]{4,20}$/', $path)) {
$stmt = $pdo->prepare('SELECT url FROM links WHERE code = ?');
$stmt->execute([$path]);
$url = $stmt->fetchColumn();
if (!$url) {
response(404, '短链接不存在', null, 404);
}
$pdo->prepare('UPDATE links SET clicks = clicks + 1 WHERE code = ?')->execute([$path]);
header('Location: ' . $url, true, 302);
exit;
}
response(404, '接口不存在', null, 404); 本地测试:
# 启动服务
php -S 127.0.0.1:8000 shortlink-api.php
# 创建短链
curl -X POST http://127.0.0.1:8000/api/short-links -H 'Content-Type: application/json' -d '{"url":"https://example.com"}'
# 访问返回中的 short_url 即可跳转