基于实现的接口强制定义函数


forcing definition of a function based on interface implemented

我正在使用一些数据库多态性来通过雄辩/lavel连接表关系。(注意,下面的例子已经简化了,这两个对象已经在扩展一个基类,所以我不能扩展另一个实现我想要的行为的基类,它们扩展的基类与其他类共享,这些类与我下面要做的无关)

class Pageable{
  public function table() {
    return $this->morphTo();
  }
}
class User {
  public function pageable() {
    return $this->morphOne('Pageable', 'table');
  }
  public function returnUrl() {
    return "http://...";
  }
}
class Company {
  public function pageable() {
    return $this->morphOne('Pageable', 'table');
  }
  public function returnUrl() {
    return "http://...";
  }  
}

我遍历pageable,然后可以检索User或Company对象,但我需要一个通用函数,如returnUrl,我可以调用任何可能被变形为该关系的对象。有没有任何方法可以在上面清理这个问题,或者至少创建一些故障安全检查,以确保所有所需的方法都在类中实现,例如,如果它们实现了PeageableInterface。例如,我可以在接口中设置一个要求,要求这个returnUrl函数是必需的吗?

我将如何创建这样的界面?

尝试使用traits。

在你的课堂上,只需做以下事情:

use TraitWithReturnUrl;

然后。。。

trait TraitWithReturnUrl {
    function returnUrl() {
        // do stuff like it's on the object itself
    }
}

宾果!:)

还可以查看我的Fatty库,它也可以用于以下内容:https://github.com/kirkbushell/fatty

在这两种情况下,您都需要PHP 5.4+。

特性可能是一种更好的方法(php 5.5中的新方法),但您可以直接使用接口,我认为在您的情况下可能是这样的:

1) 创建一个接口:

interface Pageable {
    public function pageable();
}

2) 实现接口

class User extends Model implements UserInterface, RemindableInterface, Pageable {
    ... other methods ...
    public function pageable() {
        return $this->morphOne('Pageable', 'table');
    }
}

然而,如果方法pageable()在每个实现中都是完全相同的代码,那么您可能需要创建一个定义它的抽象类,然后将其用作模型的基类:

use Illuminate'Database'Eloquent'Model as BaseModel;
abstract class NewModel extends BaseModel implements Pageable {
    public function pageable() {
        return $this->morphOne('Pageable', 'table');
    }
}

然后你的课程:

class User extends NewModel implements UserInterface, RemindableInterface {
    // You now have the pageable() method available
}

希望这能帮助你找到正确的方向。