composer引入本地自己開發的php擴充套件包

老猫不爱吃鱼發表於2024-11-26

開發自己的php擴充套件包

一、建立擴充套件包目錄結構

1. 建立目錄hoo-tool,在目錄下建立目錄 src
2. 在hoo-tool 目錄下 執行命令:composer init

3. 執行完命令的效果

{
    "name": "hoo/tool",
    "description": "hoo Tool kit for PHP",
    "type": "library",
    "license": "MIT",
    "autoload": {
        "psr-4": {
            "Hoo\\Tool\\": "src/"
        }
    },
    "authors": [
        {
            "name": "hoo",
            "email": "hoo@example.com"
        }
    ],
    "minimum-stability": "alpha",
    "require": {}
}

二、編寫composer.json檔案

本文PHP版本是使用8.2
所以在composer.json 中編寫,指定require的PHP版本:

"require": {
        "php": ">=8.0"
    }

三、編寫擴充套件包的PHP程式碼

1. 編寫一個響應工具,Hoo\Tool這個名稱空間對應src目錄

在src目錄下建立 ResultTool.class類

<?php

namespace Hoo\Tool;


use Hoo\Tool\Constants\ErrorCode;

class ResultTool
{
    /**
     * @param array $data
     * @return array
     */
    public static function success(array $data = []): array
    {
        return static::end(ErrorCode::SUCCESS, ErrorCode::getMessage(ErrorCode::SUCCESS), $data);
    }

    /**
     * @param int $code
     * @param string $message
     * @param array $data
     * @return array
     */
    public static function error(string $message = '', int $code = ErrorCode::ERROR, array $data = []): array
    {
        if (empty($message)) {
            return static::end($code, ErrorCode::getMessage($code), $data);
        } else {
            return static::end($code, $message, $data);
        }
    }

    /**
     * @param $code
     * @param $message
     * @param $data
     * @return array
     */
    protected static function end($code, $message, $data): array
    {
        return [
            'code' => $code,
            'message' => $message,
            'data' => $data,
        ];
    }
}
2. 編寫一個響應工具的狀態碼類

src目錄下建立Constants目錄
建立ErrorCode.class

<?php

namespace Hoo\Tool\Constants;

class ErrorCode
{

    public const SUCCESS = 200;
    public const ERROR = 0;

    public static function getMessage(int $code): string
    {
        $errors = [
            0 => 'Server Error!',
            200 => 'success',
            // Add more as needed
        ];

        return $errors[$code] ?? 'Unknown error';
    }
}
3. 再編寫一個日誌工具

在src目錄建立 LoggerUtil.class類

<?php

namespace Hoo\Tool;


class LoggerUtil
{
    private string $filePath;
    private string $dirName = './runtime/logs/'; // 日誌檔案目錄
    private float|int $maxFileSize = 2 * 1024 * 1024; // 2MB 檔案大小限制
    private string $datePattern = 'Y-m-d'; // 日誌檔案命名中的日期格式
    private bool $rollingType = true; // true按檔案大小滾動,false按日期滾動

    /**
     * 檢查並執行日誌檔案的滾動
     */
    private function checkAndRollFile()
    {
        $dir_path = dirname($this->filePath);
        if (!file_exists($dir_path)) {
            mkdir($dir_path, 0755, true); // 0755 表示許可權,true 表示遞迴建立
        }

        // 檢查是否需要按日期滾動
        if (!$this->rollingType && file_exists($this->filePath) && date($this->datePattern) !== date($this->datePattern, filemtime($this->filePath))) {
            $this->rollByDate();
        }

        // 檢查檔案大小
        clearstatcache(true, $this->filePath);
        if ($this->rollingType && file_exists($this->filePath) && filesize($this->filePath) >= $this->maxFileSize) {
            $this->rollBySize();
        }
    }

    /**
     * 按日期滾動日誌檔案
     */
    private function rollByDate()
    {
        $newPath = $this->getNewFilePath(true);
        rename($this->filePath, $newPath);
    }

    /**
     * 按大小滾動日誌檔案
     */
    private function rollBySize()
    {
        $newPath = $this->getNewFilePath(false, true);
        rename($this->filePath, $newPath);
    }

    /**
     * 獲取新日誌檔案的路徑
     *
     * @param bool $byDate 是否按日期滾動
     * @param bool $forcedBySize 是否因檔案大小強制滾動
     * @return string 新的日誌檔案路徑
     */
    private function getNewFilePath($byDate = false, $forcedBySize = false)
    {
        $baseName = pathinfo($this->filePath, PATHINFO_FILENAME);
        $extension = pathinfo($this->filePath, PATHINFO_EXTENSION);
        $dirName = pathinfo($this->filePath, PATHINFO_DIRNAME);

        $suffix = '';
        if ($byDate) {
            $suffix = '_' . date($this->datePattern);
        } elseif ($forcedBySize) {
            $suffix = '_size_' . date('Hi');
        }

        return "{$dirName}/{$baseName}{$suffix}.{$extension}";
    }

    /**
     * 寫入日誌內容
     *
     * @param string $fileName
     * @param mixed $content
     * @param string $label
     * @return bool
     */
    public static function write(string $fileName, mixed $content, string $label = ''): bool
    {
        $instance = new self();
        $instance->filePath = $instance->dirName . date('Ymd') . '/' . $fileName . '.log';
        $instance->checkAndRollFile();
        if (is_string($content)) {
            $content = "[" . date("Y-m-d H:i:s") . "] " . $label . ' ' . $content . PHP_EOL;
        } else {
            $content = "[" . date("Y-m-d H:i:s") . "] " . $label . PHP_EOL . var_export($content, true) . PHP_EOL;
        }

        // 寫入日誌
        $result = file_put_contents($instance->filePath, $content, FILE_APPEND);

        return $result !== false;
    }


}

引入自己開發的包

1. 編輯composer.json檔案

在專案中引入未提交的包

"repositories": [
    {
      "type": "path",
      "url": "包的覺得路徑"
    }
  ]

url的配置示例:

  • windows "D:\docker-code\code\hoo-tool"
  • linux:"/code/hoo-tool"
2. 引入包

composer require hoo/tool

3. 使用包
<?php

declare(strict_types=1);

namespace App\Controller;

use HooTool\LoggerUtil;
use HooTool\ResultTool;

class IndexController extends AbstractController
{
    public function index()
    {
        LoggerUtil::write('test',' Check If The Application Is Under Maintenance','test');
		return ResultTool::success('獲取成功',[
            'method' => 'post',
            'message' => "Hello hoo-tool",
        ]);
        return ResultTool::error('伺服器錯誤',500,[
            'method' => 'post',
            'message' => "Hello hoo-tool",
        ]);
    }
}

相關文章