2

我正在开发一个 Zend Framework (1.11) 应用程序,我将其移植到模块中,以便开发人员可以插入和播放我们软件的各种添加内容,也可以轻松删除。

我遇到的问题(并且似乎无法找到答案)我有可靠的库代码,即我的结构目前是这样

- application
  - (the standard ZF stuff)
  - modules
     - testModule
        - Bootstrap.php
        - controllers
        - configs
        - views
 - library
    - CoreStuff
       - Class.php
       - SpecialClass.php
    - testModuleLibrary
       - Class.php
       - SpecialClass.php

而我真正想要的是这样,以便其他开发人员更容易将模块安装到我们的系统中。

 - application
   - (the standard ZF stuff)
   - modules
      - testModule
         - Bootstrap.php
         - controllers
         - configs
         - views
         - library
            - Class.php
            - SpecialClass.php
 - library
    - CoreStuff
       - Class.php
       - SpecialClass.php

我可以在模块 Bootstrap 中使用 Autoloader 吗?还是我必须将它添加到我的包含路径中?

[编辑]

这是我当前的模块引导程序,我用危险的谷歌搜索一次又一次地看到这段代码,但它似乎没有任何区别

<?php

    class Notifications_Bootstrap extends Zend_Application_Module_Bootstrap {

        protected function _initLibraryAutoloader () {
            return $this->getResourceLoader()->addResourceType('library', 'library', 'library');
        }

}
4

4 回答 4

1

您可以在应用程序配置文件中定义您的库路径,例如:这是 YML 中的示例

project:
    bootstrap:
        path: APPLICATION_PATH/Bootstrap/index.php
        class: Bootstrap_Index
    Autoloadernamespaces:
        - Zend_
        - Library1_
        - Library2_
    resources:
        FrontController:
            moduledirectory:
                - APPLICATION_PATH/modules
......

这是 INI 格式的示例

[bootstrap]
        Autoloadernamespaces[] = "Zend_"
        Autoloadernamespaces[] = "Library1_"
        Autoloadernamespaces[] = "Library2_"

        resources.FrontController.moduleDirectory = APPLICATION_PATH"/modules"
        resources.FrontController.resetRouterOnEveryRequest = true

        bootstrap.path = APPLICATION_PATH "/Bootstrap/index.php"
        bootstrap.class = "Bootstrap_Index"

关于项目目录结构,我建议您使用类似于:

- application 
    - Bootstrap
        - index.php
    - Modules
        - Mod1
            - controllers
            - views
        - Mod2
            - controllers
            - views
        ...
- library 
    - Zend
        - ...
    - Library1
        - ...
    - Library2
        - ...

完成目录结构后,您可以拥有像 /:module/:controller/:action 这样的 URL,并将所有第 3 方代码分开保存在自己的池库目录中

于 2012-11-15T10:26:48.627 回答
1

我已经用以下代码解决了我的问题。我真的不知道为什么我没有早点想出这个:( :(

class Notifications_Bootstrap extends Zend_Application_Module_Bootstrap {
    protected function _initConfig () {
        set_include_path(implode(PATH_SEPARATOR, array(
            dirname(__FILE__) . '/library',
            get_include_path(),
        )));
    }
}
于 2012-11-14T15:25:02.873 回答
0

我添加此回复希望既能回答原始查询,又能对此处提交的一些项目进行澄清。我是 ZF 1.11 中模块的活跃开发人员,并且在我们维护的几个模块之一中使用我每天将要解释的内容。

对于此回复的长度,我提前道歉。有几个项目需要涵盖和考虑。

首先,对于实施。

据我所知,提供的以下代码段在 1.8 左右工作,而不是您想要的 1.11。

<?php

class Notifications_Bootstrap extends Zend_Application_Module_Bootstrap {

    protected function _initLibraryAutoloader () {
        return $this->getResourceLoader()->addResourceType('library', 'library', 'library');
    }

}

如果我将在下面解释一些关键元素,以下内容将可以正常工作。

protected function _initLibraryAutoloader () {
    return $this->getResourceLoader()->addResourceType('library', 'library', 'Library_');
}

您会注意到第三个参数(命名空间)略有不同。对此的最佳解释是可能将函数更新为以下内容:

protected function _initLibraryAutoloader () {
    $this->getResourceLoader()->addResourceType('library', 'library', 'Library_');
    var_dump($this->getResourceLoader()->getResourceTypes());die;
}

您的输出应该类似于:

Array
(
[dbtable] => Array
    (
        [namespace] => Admin_Model_DbTable
        [path] => /path/to/trunk/application/modules/admin/models/DbTable
    )

[mappers] => Array
    (
        [namespace] => Admin_Model_Mapper
        [path] => /path/to/trunk/application/modules/admin/models/mappers
    )

[form] => Array
    (
        [namespace] => Admin_Form
        [path] => /path/to/trunk/application/modules/admin/forms
    )

[model] => Array
    (
        [namespace] => Admin_Model
        [path] => /path/to/trunk/application/modules/admin/models
    )

[plugin] => Array
    (
        [namespace] => Admin_Plugin
        [path] => /path/to/trunk/application/modules/admin/plugins
    )

[service] => Array
    (
        [namespace] => Admin_Service
        [path] => /path/to/trunk/application/modules/admin/services
    )

[viewhelper] => Array
    (
        [namespace] => Admin_View_Helper
        [path] => /path/to/trunk/application/modules/admin/views/helpers
    )

[viewfilter] => Array
    (
        [namespace] => Admin_View_Filter
        [path] => /path/to/trunk/application/modules/admin/views/filters
    )

[library] => Array
    (
        [namespace] => Admin_Library
        [path] => /path/to/trunk/application/modules/admin/library
    )

)

如果您将其与之前的“库”作为第三个参数进行比较,您很快就会明白为什么它会产生如此重要的差异。

重申一下,此时,您已经声明了一个带有“Library_”前缀的库类型,它转换为“Admin_Library”。现在,要实现这一点,您将在模块中拥有库文件夹,就像在主应用程序模块中一样,只需稍作调整。要拥有一个 Admin 模块特定的控制器操作 (Admin_Library_Controller_Action),您将拥有 library/Controller/Action.php,其类名为 Admin_Library_Controller_Action。这是大多数人一开始会感到困惑的地方,但它与您应该在模块中使用的其他资源命名空间非常相似。

技术解释到此结束。如果您不再阅读,您将能够拥有一个特定于您的模块并且完全独立的库,以便于复制/粘贴可重用模块的实现。

现在对我在这里看到的其他一些回复发表一些评论。

无穷大

“如果您遵循您的结构,您最终可能会得到 - Module1 (Lib1, Lib2) - Module2 (Lib1, Lib3),因此您将开始复制所需的库。”

这在技术上是正确的,但如果您发现自己经常在各处使用相同的库,则确实会在您的实际开发风格中带来更多问题。我们通常将这些公共项目存储在另一个库中,我们将其用作外部库,与 Zend 相同,并与 Zend 并排放置在主应用程序库文件夹中。

如果您已经这样做了,我认为可能需要进一步澄清的是,如果您正确使用命名空间,您绝对不必担心库类名的冲突。您可能会在短时间内发现您需要在多个模块中拥有具有相同代码的类,但是一旦发生这种情况,您应该考虑除了我上面提到的 Zend 之外的通用库。

我再次为这个回复的长度道歉。我希望它可以帮助任何可能遇到这篇文章需要在模块中实现库的人。

于 2013-01-17T19:58:33.257 回答
0

您可以只使用模块的 Boostrap.php。提供一个函数

protected function _initAutoload(){}

使库可用。因此,您可以让模块开发人员去做,因为它是开发模块以使其资源可加载的工作的一部分:)

于 2012-11-14T12:11:53.827 回答