php Composer自动载入文件夹中的多个档案

q9yhzks0  于 2022-11-28  发布在  PHP
关注(0)|答案(3)|浏览(168)

我在最新的项目中使用了composer,并将函数Map为

"require": {
    ...
},
"require-dev": {
    ...
},
"autoload": {
    "psr-4": {
        ...
    },
    "files": [
        "src/function/test-function.php"
    ]
}

我想象会有很多文件在一个文件夹功能,ex:real-function-1.php、real-function-2.php等。那么,composer是否可以调用文件夹中的所有文件function?i懒于使用

"files": [
     "src/function/real-function-1.php",
     "src/function/real-function-2.php",
     ..,
     "src/function/real-function-100.php",
]

有没有像我这样懒的......

pexxcrt2

pexxcrt21#

如果你不能命名你的函数(因为它会打断一堆代码,或者因为你不能使用PSR-4),并且你不想创建静态类来保存你的函数(然后可以自动加载),你可以创建你自己的全局包含文件,然后告诉composer包含它。

编写器.json

{
    "autoload": {
        "files": [
            "src/function/include.php"
        ]
    }
}

包括.php

$files = glob(__DIR__ . '/real-function-*.php');
if ($files === false) {
    throw new RuntimeException("Failed to glob for function files");
}
foreach ($files as $file) {
    require_once $file;
}
unset($file);
unset($files);

这是不理想的,因为它将为每个请求加载每个文件,而不管其中的函数是否被使用,但它将工作。
注意:确保include文件在/real-function或类似的目录之外,否则它也会包含自身,变成递归函数,最终抛出内存异常。

yacmzcpb

yacmzcpb2#

现在有一个更好的方法来完成这个任务,而不需要任何自定义代码。如果你使用的是类,你可以使用Composer的classmap特性。如果你使用的是包含函数的单个文件,那么你必须使用files[]数组。

{
    "autoload": {
        "classmap": ["src/", "lib/", "Something.php"]
    }
}
mwecs4sa

mwecs4sa3#

这整个过程可以完全自动化,同时仍然相对良好地执行。
使用以下package.json(注意缺少自动加载条目,但是可以添加其他条目)

{
  "scripts": {
    "pre-autoload-dump": "\\MyComponentAutoloader::preAutoloadDump"
  }
}

然后......

<?php

class MyComponentAutoloader
{
    public static function preAutoloadDump($event): void
    {
        $optimize = $event->getFlags()['optimize'] ?? false;
        $rootPackage = $event->getComposer()->getPackage();

        $dir = __DIR__ . '/../lib'; // for example

        $autoloadDefinition = $rootPackage->getAutoload();
        $optimize
            ? self::writeStaticAutoloader($dir)
            : self::writeDynamicAutoloader($dir);
        $autoloadDefinition['files'][] = "$dir/autoload.php";
        $rootPackage->setAutoload($autoloadDefinition);
    }

    /**
     * Here we generate a relatively efficient file directly loading all
     * the php files we want/found. glob() could be replaced with a better
     * performing alternative or a recursive one.
     */
    private static function writeStaticAutoloader($dir): void
    {
        file_put_content(
            "$dir/autoload.php",
            "<?php\n" . 
            implode("\n", array_map(static function ($file) {
                return 'include_once(' . var_export($file, true) . ');';
            }, glob("$dir/*.php"))
        );
    }

    /**
     * Here we generate an always-up-to-date, but slightly slower version.
     */
    private static function writeDynamicAutoloader($dir): void
    {
        file_put_content(
            "$dir/autoload.php",
            "<?php\n\nforeach (glob(__DIR__ . '/*.php') as \$file)\n 
   include_once(\$file);"
        );
    }
}

注意事项:

  1. preAutoloadDump负责将autoload.php入口点添加到composer。
    1.每次转储自动加载器时都会生成autoload.php(例如composer install/composer update/composer dump-autoload
    1.转储优化的自动加载器(composer dump-autoload --optimize)时,将仅加载在该点找到的文件。
    1.您还应该将autoload.php添加到.gitignore

相关问题