codeigniter 重写随Composer安装的库中的类的策略

lawou6xi  于 2023-09-28  发布在  其他
关注(0)|答案(5)|浏览(144)

我正在使用Codeigniter和Composer。其中一个要求是PHPEcel。现在我需要改变一个类中的函数。什么是最好的策略呢?我应该更改供应商文件夹中的代码吗?如果是,如何在所有示例中维护更改?如果不是,我该如何重写这个特定的类。虽然我提到了PHPEcel,但我想要一个通用的解决方案。
我不确定这是否是讨论这个问题的合适论坛。如果没有,我会删除它。如果需要更多的细节,请告诉我。
谢谢

tvmytwxo

tvmytwxo1#

在composer.json中,在[“autoload”][“psr-4”]下,添加一个以namespace为键,path为值的条目:

{
     "autoload": {

         "psr-4": {

             "BuggyVendor\\Namespace\\": "myfixes/BuggyVendor/Namespace"
         }
     }
}

将您要覆盖的文件复制到该路径下(保持子命名空间目录结构),并在那里编辑它们。它们将优先于库包的原始“类路径”。看起来,以这种方式添加到composer.json的namespace->pathMap被认为是在所需包添加的那些之前。注意:我只是尝试了一下,它的工作,虽然我不知道这是一个预期的功能或什么可能的陷阱。
编辑:找到了一个Gotcha。有时候,当您随后需要另一个带有composer require vendor/package的包时,您将“丢失”覆盖。如果发生这种情况,您必须手动发出composer dump-autoload。这将恢复正确的自动加载顺序,以执行您的覆盖。

velaa5lx

velaa5lx2#

将最后两行添加到composer.jsonautoload部分,当我只想覆盖vendors目录中的一个文件时,这对我很有效:

"autoload": {        
    "classmap": [
        "database"
    ],
    "psr-4": {
        "App\\": "app/"
    },
    "exclude-from-classmap": ["vendor/somepackagehere/blah/Something.php"],
    "files": ["app/Overrides/Something.php"]
},

请记住,app/Overrides/Something.php中的名称空间需要与vendor/somepackagehere/blah/Something.php中的原始名称空间相匹配。
请记住在编辑composer.json后运行composer dump-autoload
文档:https://getcomposer.org/doc/04-schema.md#files

wdebmtf2

wdebmtf23#

还有一个选择如果您需要重写唯一的类,您可以像这样使用composer.json中的文件

"autoload": {
     "files": ["path/to/rewritten/Class.php"]
  }

所以如果你想重写类Some\Namespace\MyClass,就像这样写

#path/to/rewritten/Class.php

namespace Some\Namespace;

class MyClass {
  #do whatever you want here
}

在每次请求时,composer都会将该文件加载到内存中,因此当需要使用Some\Namespace\MyClass时,将使用path/to/rewritten/Class.php的实现。

2o7dmzc5

2o7dmzc54#

您也可以简单地复制该文件,并覆盖原始文件与您自己的。假设创建一个目录,例如“vendor-overrides”,您可以将固定文件放置在其中,只需将此添加到您的composer:

"scripts": {
    "post-install-cmd": [
      "@php -r \"copy('vendor-overrides/path/to/your/fixed/file.php', 'vendor/path/to/your/broken/file.php');\""
    ],
    "post-update-cmd": [
"@php -r \"copy('vendor-overrides/path/to/your/fixed/file.php', 'vendor/path/to/your/broken/file.php');\""
    ]
  }
oyxsuwqo

oyxsuwqo5#

更改现有类违反OOP和SOLID原则(对扩展开放/对修改原则关闭)。因此,这里的解决方案不是直接更改代码,而是扩展代码以添加功能。
在一个理想的世界里,你永远不应该改变一段你不拥有的代码。事实上,使用composer你不能这样做,因为当更新依赖项时,你的更改将被覆盖。
在这种情况下,一种解决方案是在应用程序级别创建一个类,并扩展要更改的类(在库级别),以便用代码重写。如果你不知道如何在PHP中扩展一个类,请看看。
然后通常,你加载你的类而不是他们的类,这样,你在他们的功能之上添加你的功能,并且在更新的情况下,没有任何中断(在非中断更新的情况下)。

相关问题