junit--基于测试开发和cobertura框架

1.什么是基于测试的开发

正常的开发流程:编码-->测试-->重复-->提交

基于测试的开发流程:测试-->编码-->重复-->提交

先写了测试之后,由于测试覆盖率要求为100%,所以就会让代码中可能存在的分支都进行测试,这样过先写测试单元,可以为将来的代码提供一种有效的参考


基于测试的开发例子:

编写接口:

package com.qunar.service;

import com.qunar.model.User;

public interface IUserService {
	public void add(User user);

	public void delete(String username);

	public User loader(String username);

	public User login(String username, String password);
}
2.针对接口进行测代码的编写 注意要覆盖每个方面

package com.qunar.service;

import static org.junit.Assert.*;

import org.junit.Before;
import org.junit.Test;

import com.qunar.model.User;
import com.qunar.model.UserException;
import com.qunar.service.impl.UserServiceByMap;

public class TestUserService {
	private IUserService us;
	private User baseUser;

	@Before
	public void setUp() {
		// init
		us = new UserServiceByMap();
		baseUser = new User("admin", "123", "管理员");
	}

	@Test
	public void testAdd() {
		User user = baseUser;
		us.add(user);
		User user2 = us.loader("admin");
		assertNotNull(user2);
		assertTrue(user.equals(user2));
	}

	@Test
	public void testDelete() {
		us.add(baseUser);
		User tUser = us.loader(baseUser.getUsername());
		assertNotNull(tUser);
		us.delete(baseUser.getUsername());
		tUser = us.loader(baseUser.getUsername());
		assertNull("删除的用户还存在",tUser);
	}

	@Test
	public void testLogin() {
		us.add(baseUser);
		String username = "admin";
		String password = "123";
		User user = us.login(username, password);
		assertTrue(user.equals(baseUser));
	}

	@Test(expected = UserException.class)
	public void testNotExistsUserLogin() {
		us.add(baseUser);
		String username = "admin1";
		String password = "123";
		us.login(username, password);
	}

	@Test(expected = UserException.class)
	public void testPasswordErrorUserLogin() {
		us.add(baseUser);
		String username = "admin";
		String password = "1234";
		us.login(username, password);
	}
}

3.编写实现类

package com.qunar.service.impl;

import java.util.Map;

import com.google.common.collect.Maps;
import com.qunar.model.User;
import com.qunar.model.UserException;
import com.qunar.service.IUserService;

public class UserServiceByMap implements IUserService {

	private Map<String, User> map = Maps.newHashMap();
 	@Override
	public void add(User user) {
 		if (loader(user.getUsername())!=null) {
			throw new UserException("用户名已经存在");
		}
 		map.put(user.getUsername(), user);
	}

	@Override
	public void delete(String username) {
		map.remove(username);
	}

	@Override
	public User loader(String username) {
		// TODO Auto-generated method stub
		return map.get(username);
	}

	@Override
	public User login(String username, String password) {
		User user = loader(username);
		if(user==null){
			throw new UserException("用户名不存在");
		}
		if(user.getPassword()!= password){
			throw new UserException("用户密码不正确");
		}
		return user;
	}
	
}

运行testCase 全部通过

如果在实现类中,当删除用户名为admin的时候不允许删除,如下所示


public void delete(String username) {
		if(username.equals("admin")){
			return ;
		}
		map.remove(username);
	}

再次运行测试代码:

java.lang.AssertionError: 删除的用户还存在
	at org.junit.Assert.fail(Assert.java:93)
	at org.junit.Assert.assertTrue(Assert.java:43)
	at org.junit.Assert.assertNull(Assert.java:551)
	at com.qunar.service.TestUserService.testDelete(TestUserService.java:39)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:606)
	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:45)
	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:42)
	at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
	at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:263)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:68)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:47)
	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229)
	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:300)
	at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
	at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

这样可以明确的指出那里出了错误

2.cobertura 的使用

1)首先修改工程的pom.xml文件 加入如下代码

<reporting>
        <plugins>
            <plugin>
                <groupId>org.codehaus.mojo</groupId>
                <artifactId>cobertura-maven-plugin</artifactId>
                <version>2.5.1</version>
            </plugin>
        </plugins>
    </reporting>

首先运行“mvn cobertura:help”, 如果不能运行,请添加以下仓库

    <pluginRepositories>
        <pluginRepository>
            <id>Codehaus repository</id>
            <url>http://repository.codehaus.org/</url>
        </pluginRepository>
    </pluginRepositories>

cobertura插件的命令

mvn cobertura:help          查看cobertura插件的帮助
mvn cobertura:clean         清空cobertura插件运行结果
mvn cobertura:check         运行cobertura的检查任务
mvn cobertura:cobertura     运行cobertura的检查任务并生成报表,报表生成在target/site/cobertura目录下
cobertura:dump-datafile     Cobertura Datafile Dump Mojo
mvn cobertura:instrument    Instrument the compiled classes

到项目根目录下运行mvn cobertura:cobertura 将会插桩class文件、测试、生成覆盖率报告

我的测试代码生产的报表如下:





  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值