[WordPress] 開發常用函式(Function)方法

本篇文章更新時間:2022/05/18
如有資訊過時或語誤之處,歡迎使用 Contact 功能通知。
一介資男的 LINE 社群開站囉!歡迎入群聊聊~
如果本站內容對你有幫助,歡迎使用 BFX Pay 加密貨幣新台幣 贊助支持。


這篇來整理一下最近開發專案時,發現有不少可以復用的方法。

不全然都是使用 WordPress 內建提供的方法,有時候會是在非 WordPress 安裝的環境驗證演算法與操作,效率更高。

之後有常用的方法就來更新這篇~

需要網路爬取資料(API請求)

function mxp_do_request(string $url, string $type = 'GET', array $headers = [], array $post_fields = [], string $user_agent = '', string $referrer = '', bool $follow = true, bool $use_ssl = false, int $con_timeout = 10, int $timeout = 40) {
    $crl = curl_init($url);
    curl_setopt($crl, CURLOPT_CUSTOMREQUEST, $type);
    curl_setopt($crl, CURLOPT_USERAGENT, $user_agent);
    curl_setopt($crl, CURLOPT_REFERER, $referrer);
    if ($type == 'POST') {
        curl_setopt($crl, CURLOPT_POST, true);
        if (!empty($post_fields)) {
            curl_setopt($crl, CURLOPT_POSTFIELDS, $post_fields);
        }
    }
    if (!empty($headers)) {
        curl_setopt($crl, CURLOPT_HTTPHEADER, $headers);
    }
    curl_setopt($crl, CURLOPT_FOLLOWLOCATION, $follow);
    curl_setopt($crl, CURLOPT_CONNECTTIMEOUT, $con_timeout);
    curl_setopt($crl, CURLOPT_TIMEOUT, $timeout);
    curl_setopt($crl, CURLOPT_SSL_VERIFYHOST, $use_ssl);
    curl_setopt($crl, CURLOPT_SSL_VERIFYPEER, $use_ssl);
    curl_setopt($crl, CURLOPT_ENCODING, 'gzip,deflate');
    curl_setopt($crl, CURLOPT_RETURNTRANSFER, true);
    $call_response = curl_exec($crl);
    curl_close($crl);
    return $call_response; //Return data
}

上面是 PHP cURL 實作的版本,下方則是套用 WordPress 內建方法的改版,同樣參數,替換實作內容就可以無縫切入。

function mxp_do_request(string $url, string $type = 'GET', array $headers = [], array $post_fields = [], string $user_agent = '', string $referrer = '', bool $follow = true, bool $use_ssl = false, int $con_timeout = 10, int $timeout = 40) {
    $args = array(
        'method'      => $type,
        'timeout'     => $timeout,
        'redirection' => 5,
        'httpversion' => '1.1',
        'blocking'    => true,
        'sslverify'   => $use_ssl,
        'headers'     => [
            'User-Agent' => $user_agent,
            'Referer'    => $referrer,
        ],
        'body'        => $post_fields,
    );
    if (!empty($headers) && count($headers) != 0) {
        foreach ($headers as $key => $header) {
            $args['headers'][$key] = $header;
        }
    }
    $response = wp_remote_request($url, $args);
    $body     = wp_remote_retrieve_body($response);

    return $body;
}

下載檔案

cURL 簡易的下載檔案方式,適用下載檔案資源路徑(URL)包含檔案名稱與檔案類型(MIME Type)明確不帶其他 Query String 的作法

function mxp_download_source($url, $name) {
    $name_path = $name;
    $suffix    = end(explode('.', $url));
    $file_name = dirname(__FILE__) . "/" . $name_path . "." . $suffix;
    if (file_exists($file_name)) {
        return $file_name;
    }
    $fp = fopen($file_name, 'w+');
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_FILE, $fp);
    $data = curl_exec($ch);
    curl_close($ch);
    fclose($fp);
    fputs($fp, $data);
    fclose($fp);
    return $file_name;
}

下載 .gz 壓縮格式的檔案,並解壓縮

function mxp_download_source($url) {
    $path          = basename(parse_url($url, PHP_URL_PATH));
    $file_name     = dirname(__FILE__) . "/" . $path;
    $buffer_size   = 4096; // read 4kb at a time
    $out_file_name = str_replace('.gz', '', $file_name);
    if (file_exists($out_file_name)) {
        return $out_file_name;
    }
    $fp = fopen($file_name, 'w');
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_FILE, $fp);
    $data = curl_exec($ch);
    curl_close($ch);
    fclose($fp);
    $file     = gzopen($file_name, 'rb');
    $out_file = fopen($out_file_name, 'wb');
    while (!gzeof($file)) {
        fwrite($out_file, gzread($file, $buffer_size));
    }
    fclose($out_file);
    gzclose($file);
    unlink($file_name);
    return $out_file_name;
}

算文字檔案總行數(適用大檔案)

//https://stackoverflow.com/questions/2162497/efficiently-counting-the-number-of-lines-of-a-text-file-200mb
$file = new SplFileObject($source_file);
$file->seek(PHP_INT_MAX);
$total_lines = $file->key() + 1;

照行數讀取文字檔案內容

    $file        = new SplFileObject($filename);
    $line        = '';
    $file_number = get_total_lines($filename);
    $left_items  = $file_number % 5000;
    for ($i = 1; $i <= $file_number; ++$i) {
        if (!$file->eof()) {   
            //https://stackoverflow.com/questions/5775452/php-read-specific-line-from-file
            $file->seek($i);//帶入行號
            $line    = $file->current();//取得該行內容
        }
    }

下載遠端圖片並上傳 WordPress 媒體庫與加入文章精選圖片

function mxp_download_and_insert_wp($link = '', $author_id = 1, $post_parent = 0, $att_title = '', $att_content = '', $set_post_thumbnail = true) {
    if ($link == '') {
        return false;
    }
    require_once ABSPATH . 'wp-admin/includes/media.php';
    require_once ABSPATH . 'wp-admin/includes/file.php';
    require_once ABSPATH . 'wp-admin/includes/image.php';
    $filename    = basename(parse_url($link, PHP_URL_PATH));
    $options     = array('timeout' => 300);
    $upload_file = null;
    $response    = wp_safe_remote_get($link, $options);
    if (!is_wp_error($response)) {
        $data        = wp_remote_retrieve_body($response);
        $upload_file = wp_upload_bits($filename, null, $data);
    } else {
        return false;
    }
    $wp_filetype = wp_check_filetype($filename, null);
    $attachment  = array(
        'post_mime_type' => $wp_filetype['type'],
        'post_parent'    => $post_parent,
        'post_author'    => $author_id,
        'post_title'     => preg_replace('/\.[^.]+$/', '', $att_title),
        'post_content'   => $att_content,
        'post_status'    => 'inherit',
    );
    $attachment_id = wp_insert_attachment($attachment, $upload_file['file'], $post_parent);
    if (!is_wp_error($attachment_id)) {
        //產生附加檔案中繼資料
        $attachment_data = wp_generate_attachment_metadata($attachment_id, $upload_file['file']);
        wp_update_attachment_metadata($attachment_id, $attachment_data);
        //將圖像的附加檔案設為特色圖片
        $type = explode("/", $wp_filetype['type']);
        if ($set_post_thumbnail && $type[0] == 'image') {
            set_post_thumbnail($post_parent, $attachment_id);
        }
        return true;
    } else {
        return false;
    }
}

這個方法我這樣寫應該算是很 WordPress 的原生處理方式了,網路上還有其他網友分享的方法也可以參考: Gist: Upload an image to WordPress media gallery from URL

WooCommerce 訂單相關方法

以前有專門寫過一篇取訂單各項欄位資料的方法,包含顧客、訂單、結帳資料等。

參考: [WooCommerce] 程式開發時取出訂單資訊的方法整理

如果開發上或是「效能優先」的話,我會包過一個方法,一次從 postmeta 資料表裡取出訂單附加資訊,免的一個方法去呼叫一次資料庫的讀取,一次取得全部來操作,效率比較好。

function mxp_get_order_post_meta($order_id) {
    global $wpdb;
    $order_meta = $wpdb->get_results("SELECT meta_key,meta_value  FROM wp_postmeta WHERE post_id = " . $order_id, ARRAY_A);
    if (count($order_meta) == 0) {
        return false;
    }
    $arr = array();
    foreach ($order_meta as $key => $meta) {
        $arr[$meta['meta_key']] = $meta['meta_value'];
    }
    return $arr;
}

Share:

作者: Chun

資訊愛好人士。主張「人人都該為了偷懶而進步」。期許自己成為斜槓到變進度條 100% 的年輕人。[///////////____36%_________]

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *


文章
Filter
Apply Filters
Mastodon