config.yml中的SilverStripe类扩展

时间:2016-07-05 19:33:28

标签: php silverstripe

我注意到在某些情况下,当你编写一个扩展现有类的类时,你需要在config.yml文件中声明类扩展。

例如,我最近编写了此代码以删除" help" CMS后端的按钮。

mysite的/代码/ Tweak.php

class Tweak extends LeftAndMainExtension
{
  public function init()
    {
      parent::init();
      /* Remove help link */
      CMSMenu::remove_menu_item('Help');
    }
} 

mysite的/代码/ Config.yml

LeftAndMain:
  extensions:
    - Tweak

问题1:为什么需要在config.yml中声明一些类扩展?为什么这个额外的步骤不是其他类扩展所必需的(例如扩展DataObject或Page_Controller)?

问题2:有关上述代码的具体问题,为什么我在配置文件中将 Tweaks 声明为 LeftAndMain 的扩展名,但是php文件我实际上是在扩展 LeftAndMainExtension 吗?

2 个答案:

答案 0 :(得分:8)

你实际上是在谈论两种基本的OO模式。

  1. 简单的子类化
  2. 这几乎是许多语言的标准方法,包括PHP和Java,自定义类从另一个类继承一些逻辑,并能够声明自己的ala:

    class MyObject extends DataObject {
    }
    

    在这种情况下,SilverStripe没有特定的内容,在这种情况下是原生的(PHP)。

    1. 装饰者
    2. 当您继承Extension或其任何一个子类时,例如DataExtensionSiteTreeExtensionLeftAndMainExtension根据您的示例,您可以进行装饰"一个现有的类和当前的库或框架的"装饰器"的实现。图案。

      在SilverStripe中,这两种方法之间的一个很大区别是,对于子类化,新类将在数据库中创建一个新表(在其中声明$db静态)。使用装饰器(在YML中声明的一个Extension子类或通过类本身中的$extension静态),不会创建新表,您只需能够"粘贴& #34;现有对象及其表的新字段和逻辑。

      后一种方法实用的一个常见例子是Member类。对其进行子类化,无法帮助您修改/自定义SilverStripe的会员和权限系统,装饰

      请参阅SilverStripe此功能的专用页面:https://docs.silverstripe.org/en/3.3/developer_guides/extending/extensions/

答案 1 :(得分:7)

  

问题1 :为什么需要在config.yml中声明某些类扩展?为什么这个额外的步骤不是其他类扩展所必需的(例如扩展DataObject或Page_Controller)?

PHP和SilverStripe术语之间存在重要区别。

在SilverStripe中,扩展是一个在SilverStripe中实现的框架功能,它允许您修改对象的行为,而无需访问除公共内容之外的任何内容。在这方面它与Ruby类似。

在PHP中,您使用extends关键字来定义现有类的子类。

在您的示例中,您使用的是LeftAndMainExtension,这是一个SilverStripe"扩展" - 这使您可以在SilverStripe的管理区域中修改CMS菜单的行为,而不会字面上扩展(以PHP术语)LeftAndMain。 / p>

  

问题2 :有关上述代码的具体问题,为什么我在配置文件中声明 Tweaks 作为 LeftAndMain 的扩展名,但是php文件我实际上是在扩展 LeftAndMainExtension 吗?

如上所述,这就是SilverStripe的扩展系统的工作原理。它基本上遵循以下过程:

  • 您在继承中的某个位置创建了一个extends(PHP关键字)Extension的类(使用LeftAndMainExtension,它扩展了Extension)。对于DataObjects,请改用DataExtension
  • 您告诉SilverStripe将您的扩展程序应用于对象,在这种情况下它是LeftAndMain

命名是故意的,因此您可以轻松/直观地将对象及其相关扩展组合在一起:

  

约定是扩展类名称以Extension结尾。这不是一个要求,但要更清楚

     

- SilverStripe开发人员文档

注意我故意将Extension扩展为表示它是SilverStripe扩展类,而不是类(class Foo extends Bar)的PHP扩展。

有关框架如何执行此过程的示例,它基本上是这样的:

  • 对象已初始化
  • 框架分析YAML配置(或通过Object::add_extension()应用的扩展程序)扩展
  • 框架循环扩展,将$this->owner设置为当前对象,以便扩展程序可以从中访问公共方法和属性
  • Framework返回final Object

More info here.