jdk版本升级对单元测试造成的影响

单元测试的时候遇到的一个问题

开始的时候这个单元测试在eclipse和mvn中都是跑不过的(原因数据库里插入了一个非空列),然后把这个修改好,问题就开始出现了。

在eclipse中跑出来的结果是非常振奋人心的

jdk版本升级对单元测试造成的影响_第1张图片

但是通过mvn test跑出来的结果确是:

jdk版本升级对单元测试造成的影响_第2张图片

遇到了这个问题,第一反应觉得是不是因为文件没保存或者因为eclipse中装了svn插件导致的文件不同步的问题。删除eclipse中的项目,重新clean install整个pivot,在mvn eclipse:eclipse,再导入eclipse,但是没有任何效果。

然后去仔细看了一下test的日志,发现其中有很多的Exception打出来了,觉得是不是这里出现问题了。

DEBUG util.SQLHelper - Could not retrieve the 'isAutoIncrement' property because not yet running on Java 1.5 - defaulting to NO. Table=CREDIT_CMT_APPLY, Column=IS_GUAR_VALID
java.sql.SQLException: ��Ч�������� 注:这里的意思大概意思就是SQl索引失效
	at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:112)
	at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:146)
	at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:208)
	at oracle.jdbc.driver.OracleResultSetImpl.getString(OracleResultSetImpl.java:379)
	at org.dbunit.util.SQLHelper.createColumn(SQLHelper.java:348)
	at org.dbunit.database.DatabaseTableMetaData.getColumns(DatabaseTableMetaData.java:331)
	at org.dbunit.database.DatabaseTableMetaData.toString(DatabaseTableMetaData.java:402)
	at java.lang.String.valueOf(String.java:2826)
	at java.lang.StringBuffer.append(StringBuffer.java:219)

不过这个日志的级别是Debug,貌似不应该影响测试结果啊。不过还是去确定一下这个有没有影响比较好。然后找到日志打出的地方如下,发现这里只是去判断了一下jdk是1.5进行一些操作,不是也不会有什么影响。

接着去看maven输出来的test结果,发现错误信息是:

junit.framework.AssertionFailedError:null

这是个什么意思阿?然后去找了一下,发现原因是在JUnit 4.4 以前的版本默认出错后不会抛出额外提示信息,如:

assertTrue( s.indexOf("developer") > -1 || s.indexOf("Works") > -1 );

如果该断言出错,只会抛出无用的错误信息,如:junit.framework.AssertionFailedError:null。如果想在出错时想打印出一些有用的提示信息,必须得程序员另外手动写,如:

assertTrue( "Expected a string containing 'developer' or 'Works'", 
    s.indexOf("developer") > -1 || s.indexOf("Works") > -1 );
public static final Column createColumn(ResultSet resultSet,
384             IDataTypeFactory dataTypeFactory, boolean datatypeWarning) 
385     throws SQLException, DataTypeException 
386     {
387         ...
395         // This is only available since Java 5 - so we ca try it and if it does not work default it
396         String isAutoIncrement = Column.AutoIncrement.NO.getKey();
397         try {
398             isAutoIncrement = resultSet.getString(23);
399         }
400         catch(SQLException e){
401             if(logger.isDebugEnabled())
402                 logger.debug("Could not retrieve the 'isAutoIncrement' property because not yet running on Java 1.5 - defaulting to NO. " +
403                         "Table=" + tableName + ", Column=" +columnName, e);
404             // Ignore this one here
405         }
406         
407         ...
428     }
Unit 4.4 以前的版本默认出错后不会抛出额外提示信息,如:

assertTrue( s.indexOf("developer") > -1 || s.indexOf("Works") > -1 );

如果该断言出错,只会抛出无用的错误信息,如:junit.framework.AssertionFailedError:null。

如果想在出错时想打印出一些有用的提示信息,必须得程序员另外手动写,如:

assertTrue( "Expected a string containing 'developer' or 'Works'", 
    s.indexOf("developer") > -1 || s.indexOf("Works") > -1 );

既然让写,那就写一下试试。

assertTrue("number="+number,number > 0);注:原来代码里面的一个判断,想让它输出一些信息,但是发现并没有输出这个,看来不是在这里出的问题。

剩下的代码中可能出问题的一共就只有两行。

setUpDataSet("dbunit/complaintSet.xml");
Long number = this.complaintApplyDAO.insert(complaintApplyDO);

然后通过一个个注释的方法确定到问题在setUpDataSet这一行。

进一步定位发现是初始化数据的配置文件中出错了,其中一共有7条数据,通过排除法确定,问题在下面这个代码中。

<credit_cmt_apply id="10007" COMPLAINT_Id="1234567890"  C_MEMBER_ID="test100" A_MEMBER_ID="test200"
	TYPE ="cash_no_delivery" FULL_TYPE="cash_no_delivery"  SUBJECT ="subject" TRADE_ID="1001001" TRADE_TYPE="alipay" A_TEL="010-85356521" A_MOBILE_PHONE="13054541254"
	GMT_CREATE="2009-12-28"
	GMT_PRE_INTERPOSE="2010-1-26" GMT_INTERPOSE="2009-12-28" GMT_ACCEPT="2009-12-28" GMT_RESOLVE="2009-12-28" STATUS="NEW" RESULT="NEW"
	COMPANY_NAME="compay" CONTENT="content" TRADE_URL="http://china.alibaba.com"
	IS_TRANSIT="Y" IS_GUAR_VALID="Y" IS_ELIGIBLE="Y" GMT_MODIFIED="2009-12-28" A_TEL_AREA="010" SUB_TYPE="subType" GMT_ARBIT_BEGIN="2009-12-28" GMT_ARBIT_END="2009-12-28"
	ARBIT_OPERATOR="test"
	 />

经验证,问题原因是GMT_PRE_INTERPOSE="2010-1-26"这个出现的,如果将2010-1-26改成2010-01-26,则eclipse中和maven中都可以正确了。

到这里虽然确定了问题出在哪,但是进一步的思路确不是太明确了,上网找也没什么头绪。然后就开始求助于大家,最后在晓军那里得到答案,原来jdk1.6.0_18中对这个日期的处理进行了一些改动。不同版本的代码,发现改动确实在这里。
原来的java.sql.Date.ValueOf的代码如下:

public static Date valueOf(String s) {

   int year;

   int month;

   int day;

   int firstDash;

   int secondDash;

   if (s == null) throw new java.lang.IllegalArgumentException();

   firstDash = s.indexOf('-');

   secondDash = s.indexOf('-', firstDash+1);

   if ((firstDash > 0) & (secondDash > 0) & (secondDash < s.length()-1)) {

       ...
   } else {

       throw new java.lang.IllegalArgumentException();

   }        

   return new Date(year, month, day);

    }

新的中的是:

if ((firstDash > 0) && (secondDash > 0) && (secondDash < s.length()-1)) {
            String yyyy = s.substring(0, firstDash);
            String mm = s.substring(firstDash + 1, secondDash);
            String dd = s.substring(secondDash + 1);
            if (yyyy.length() == YEAR_LENGTH && mm.length() == MONTH_LENGTH &&
                dd.length() == DAY_LENGTH) {
                ...
            }
        }
        if (d == null) {
            throw new java.lang.IllegalArgumentException();
        }
        return d;


在之前的时候并不去判断年月日的长度,在新的中加入了对年份月份日的强制判断,必须是4-2-2,否则抛出异常。

最后问题定位到maven和eclipse中的java环境版本不同的问题。
通过查看确定maven中环境是:(我自己装的)

Java version: 1.6.0_20
Java home: /usr/lib/java/jdk1.6.0_20/jre

eclipse的环境是:(貌似是系统默认的一个)
jdk版本升级对单元测试造成的影响_第3张图片

你可能感兴趣的:(java,eclipse,jdk,maven,String,单元测试)