首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

PHP 實現七牛雲遠程圖片抓取與遷移完整指南

     編輯:PHP 綜合知識

隨著業務增長,公司原本存放在本地服務器的用戶頭像管理愈發吃力。為了統一資源管理、提升訪問速度,決定將所有本地頭像遷移至七牛雲存儲。本文將詳細記錄基於 PHP 實現「判斷存在 → 單個抓取 → 批量遷移」的完整技術方案,供有類似需求的開發者參考。

核心遷移邏輯

整個遷移流程可拆解為三個步驟:

  1. 存在性檢查:先查詢七牛雲是否已存在該頭像,避免重複抓取。
  2. 單文件抓取:若七牛無該文件且本地存在,調用七牛 Fetch API 將遠程圖片拉取入桶。
  3. 分批處理:通過分頁查詢數據庫,配合頁面自動跳轉防止腳本超時,逐批完成遷移。

關鍵代碼實現

1. 判斷七牛文件是否存在

利用七牛 PHP SDK 的 Qiniu_RS_Stat 接口,根據文件 Key 獲取元信息;若返回錯誤則視為不存在。

/**
 * 檢查七牛雲文件是否存在
 * @param string $url 七牛文件完整 URL
 * @return bool
 */
function url_exists($url) {
    require_once(COMMON_PATH . "qiniu/rs.php");
    require_once(COMMON_PATH . "qiniu/http.php");

    $parts = parse_url($url);
    $bucket = 'your_bucket_name';      // 替換為你的空間名
    $key    = substr($parts['path'], 1); // 去除開頭 "/"
    $accessKey = 'your_access_key';    // 替換為你的 AK
    $secretKey = 'your_secret_key';    // 替換為你的 SK

    Qiniu_SetKeys($accessKey, $secretKey);
    $client = new Qiniu_MacHttpClient(null);

    list($ret, $err) = Qiniu_RS_Stat($client, $bucket, $key);
    return $err === null;
}

2. 單個頭像抓取至七牛

結合 url_exists 與本地 file_exists 雙重校驗,調用 Qiniu_RS_Fetch 將遠程圖片「搬運」到七牛,失敗時記錄錯誤日誌便於後續排查。

/**
 * 抓取單個遠程頭像到七牛
 * @param string $remotePath 本地服務器物理路徑
 * @param string $qiniuPath  七牛目標文件 URL
 */
function oneFetch($remotePath, $qiniuPath) {
    if (!url_exists($qiniuPath) && file_exists($remotePath)) {
        require_once(COMMON_PATH . "qiniu/rs.php");
        require_once(COMMON_PATH . "qiniu/http.php");
        require_once(COMMON_PATH . "qiniu/conf.php");

        $client = new Qiniu_MacHttpClient(null);
        $accessUrl = 'https://your-domain.com/' . $remotePath; // 公開可訪問的遠程地址
        $bucket    = 'your_bucket_name';
        $key       = basename($qiniuPath); // 七牛存儲文件名

        $ret = Qiniu_RS_Fetch($client, $accessUrl, $bucket, $key);

        if ($ret === null) {
            // 記錄失敗 Key,方便人工介入
            file_put_contents('fail.log', $key . "\n", FILE_APPEND);
        } else {
            var_dump($ret); // 成功返回文件元信息
        }
    } else {
        echo '頭像已存在或本地文件缺失:' . $qiniuPath . '
'; } }

3. 批量遷移腳本(防超時設計)

採用 LIMIT offset, size 分頁查詢,每次處理 10 條記錄,通過 header("Location: ...") 實現頁面自動跳轉繼續下一批,並配合 ob_flush() flush() 實時輸出進度。

function batchMigrate() {
    header("Content-type: text/html; charset=utf-8");
    set_time_limit(0);

    $start = isset($_GET['num']) ? intval($_GET['num']) : 0;
    $limit = 10;

    // 建議改用 mysqli / PDO,此處保留原邏輯示意
    $link = mysqli_connect("localhost", "root", "root", "test");
    mysqli_set_charset($link, "utf8");

    $sql = "SELECT remotePath, qiniuPath FROM avatars ORDER BY id LIMIT {$start}, {$limit}";
    $result = mysqli_query($link, $sql);

    if (mysqli_num_rows($result)) {
        while ($row = mysqli_fetch_assoc($result)) {
            oneFetch($row['remotePath'], $row['qiniuPath']);
        }
        $next = $start + $limit;
        echo "已處理 {$next} 條記錄
"; // 自動跳轉下一批 header("Refresh:2; url=?num={$next}"); } else { echo '遷移完成!共處理 ' . $start . ' 條記錄。'; } mysqli_close($link); } // 入口調用 batchMigrate();

遷移後驗證與優化建議

  • 抽樣校驗:遷移結束後,隨機抽取若干 Key 在七牛控制台或通過 API 對比文件大小、MD5,確保數據完整。
  • 錯誤重試:針對 fail.log 記錄的失敗 Key,編寫腳本二次重試,或人工排查來源鏈接是否失效。
  • CDN 刷新:若使用了七牛 CDN,遷移完成後提交目錄刷新,確保用戶端獲取最新頭像。
  • 安全提醒:生產環境請務必將 AK/SK 配置到環境變量或加密配置文件中,切勿硬編碼在代碼裡。

通過上述方案,我們成功將數萬條本地頭像平滑遷移至七牛雲,顯著降低了本地存儲壓力,並借助 CDN 加速提升了用戶端加載體驗。希望這份實戰記錄能為你的遷移項目提供參考。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved