引用链接:http://watirmelon.com/2011/01/24/composition-or-inheritance-for-delegating-page-methods/

Composition or inheritance for delegating page methods?

The thing I like to do when creating a page object pattern for automated web testing is delegating any methods that don’t belong to the Page object itself.

For example, a very simple page object model like this GoogleHomePage doesn’t delegate any methods to the Browser object.

require "rubygems"
require "watir-webdriver" class GoogleHomePage
def initialize(browser)
@browser = browser
end
def visit
@browser.goto "www.google.com"
end
end b = Watir::Browser.new :firefox
p = GoogleHomePage.new b
p.visit
puts p.title
p.close

So, the p.title and p.close statements both fail with an error: undefined method `goto' for # (NoMethodError).

One approach would be simply to write appropriate methods for what you would do on the Browser object. For example:

require "rubygems"
require "watir-webdriver" class GoogleHomePage
def initialize(browser)
@browser = browser
end
def visit
@browser.goto "www.google.com"
end
def title
@browser.title
end
def close
@browser.close
end
end b = Watir::Browser.new :firefox
p = GoogleHomePage.new b
p.visit
puts p.title
p.close

But this isn’t DRY. It means every method of Browser you access to needs to be rewritten. But I often see this happen.

What we should be doing is simply delegating any methods that don’t exist on the Page object to the Browser object which is passed in at initialization. There are two ways I know of to do this: inheritance delegation and composition.

Inheritance Delegation

Inheritance delegation means changing our class so it delegates appropriately using a DelegateClass. This means anything of class Browser is delegated.

For example:

require "rubygems"
require "watir-webdriver" class GoogleHomePage < DelegateClass(Watir::Browser)
def initialize(browser)
super(browser)
end
def visit
self.goto "www.google.com"
end
end b = Watir::Browser.new :firefox
p = GoogleHomePage.new b
p.visit
puts p.title
p.close

From this point forward you don’t need to refer to @browser, instead you just refer to self in your class.

Composition

Composition is about composing the class of different elements, some of which are passed to the browser. This essentially involves creating a method_missing method and passing these methods to the instance variable @browser.

require "rubygems"
require "watir-webdriver" class GoogleHomePage
def initialize(browser)
@browser = browser
end
def method_missing(sym, *args, &block)
@browser.send sym, *args, &block
end
def visit
@browser.goto "www.google.com"
end
end b = Watir::Browser.new :firefox
p = GoogleHomePage.new b
p.visit
puts p.title
p.close

This means that any reference to the Browser object still needs to refer to @browser throughout the class.

Inheritance or Composition?

You can see from the examples above, both approaches are very similar, but from researching these, it seems that most people prefer composition to inheritance in ruby, mainly due to maintainability of class chains. In our example, the inheritance chain is small and very simple, so I don’t think this poses a great maintainability issue.

Composition or inheritance for delegating page methods?的更多相关文章

  1. 组合优于继承 Composition over inheritance

    https://stackoverflow.com/questions/49002/prefer-composition-over-inheritance 解答1 Prefer composition ...

  2. Effective Java 16 Favor composition over inheritance

    Inheritance disadvantage Unlike method invocation, inheritance violates encapsulation. Since you don ...

  3. React之Composition Vs inheritance 组合Vs继承

    React的组合   composition: props有个特殊属性,children,组件可以通过props.children拿到所有包含在内的子元素, 当组件内有子元素时,组件属性上的child ...

  4. Inheritance setUp() and tearDown() methods from Classsetup() and Classteardown

      I have a general test class in my nosetests suit and some sub-classes, inheriting from it. The con ...

  5. selenium page object model

    Page Object Model (POM) & Page Factory in Selenium: Ultimate Guide 来源:http://www.guru99.com/page ...

  6. <Effective C++>读书摘要--Inheritance and Object-Oriented Design<二>

    <Item 36> Never redefine an inherited non-virtual function 1.如下代码通过不同指针调用同一个对象的同一个函数会产生不同的行为Th ...

  7. inheritance in kentico

    Visual inheritance http://devnet.kentico.com/docs/7_0/devguide/index.html?visual_inheritance.htm The ...

  8. Thinking in Java——笔记(17)

    Containers in Depth Full container taxonomy You can usually ignore any class that begins with " ...

  9. 静态工厂方法VS构造器

    我之前已经介绍过关于构建者模式(Builder Pattern)的一些内容,它是一种很有用的模式用于实例化包含几个属性(可选的)的类,带来的好处是更容易读.写及维护客户端代码.今天,我将继续介绍对象创 ...

随机推荐

  1. eclipse安装M2Eclipse插件

    作者:david_zhang@sh [转载时请以超链接形式标明文章] 链接:http://www.cnblogs.com/david-zhang-index/p/7967333.html 图1: 图2 ...

  2. union联合体学习

    union,中文名“联合体.共用体”,在某种程度上类似结构体struct的一种数据结构,共用体(union)和结构体(struct)同样可以包含很多种数据类型和变量. 不过区别也挺明显: 结构体(st ...

  3. Reporting Services无法连接ORACLE,提示:System.Data.OracleClient 需要 Oracle 客户端软件 8.1.7 或更高版本

    Reporting Services无法连接ORACLE,在服务器安装ORACLE 11客户端版本后仍然提示以下错误: System.Data.OracleClient 需要 Oracle 客户端软件 ...

  4. 项目一:第五天 1、区域数据(pinyin4j-简码,城市编码) 2、Web层代码重构(model对象,分页代码提取) 3、区域分页查询 3、分区添加功能 4、定区管理管理-添加,分页

    Service: /** * @Description: 1.保存定区  2.让分区关联定区 * 对象三种状态 1.持久态(被session管理对象-一级缓存中有对象) 2.托管态(有OID标识,数据 ...

  5. 树莓派 Learning 001 装机 ---之 1 安装NOOBS系统

    树莓派安装NOOBS系统 (使用的树莓派板卡型号:Raspberry Pi 2 Model B V1.1)(板卡的型号在板子正面的丝印层上印着,你可以看到.) RASPBERRY PI 2 MODEL ...

  6. 如何将maven项目打包成可执行的jar

    如何将maven项目打包成可执行的jar 分类: maven2010-12-17 10:18 10411人阅读 评论(2) 收藏 举报 jarmavenassemblyjava 方法一:将项目及所依赖 ...

  7. 卡特兰数&错排&一个一直记不住的公式

    卡特兰数 公式:f(x)=f(2)*f(x-1)+f(3)*f(x-2)+......+f(x-1)*f(2) #include<iostream>#include<cstdlib& ...

  8. Windows环境下 Hadoop Error: JAVA_HOME is incorrectly set. 问题

    最近尝试在windows开发MR程序并且提交Job,在解压缩好Hadoop,配置好环境变量后, 打开cmd 输入hadoop version 的时候出现以下错误: Error: JAVA_HOME i ...

  9. hdu1061

    #include <iostream>#include <cstdio>using namespace std;int mod_exp(int a, int b, int c) ...

  10. Java Script 学习笔记 -- Ajax

    AJAX 一 AJAX预备知识:json进阶 1.1 什么是JSON? JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式.JSON是用字符串来表示Javas ...