Assert斷言優化

目的:spring

能夠使map,json,bean混合驗證 - assertEqual(Object,Object)json

擴展各類驗證類型,spring管理實現集。如json驗證,優化各個action調用方式。api

在testng Assert類基礎上重寫部分方法ide

 

(1)要好維護,就先定義接口優化

public interface AssertActionI<T,R> {
    /**
     *
     * @param assertinfo
     * @param actual
     * @param expect
     * @return
     */
    public boolean api_Assert(Assertinfo assertinfo, T actual, R expect);

    /**
     * 是否符合驗證類型
     * @param assertinfo
     * @param actual
     * @param expect
     * @return
     */
    public boolean matchCheckType(Assertinfo assertinfo, T actual, R expect);
}

 

 (2)以下實現 map,json,bean混合驗證 - assertEqual(Object,Object)spa

原理是都轉換成map作驗證:
json-map (原則:只取第一層的keyvalue,若是有多層請處理後再傳入)
map-map
bean-mapcode

Amap(actual)- Bmap(expect)blog

1.以expect爲驗證中心,遍歷expect的key
2.檢查actual是否存在這個key,沒有記錄錯誤信息(not check和only check 排除)
3.expect和acutal都存在key,檢查key-value
4.有not check和only check關鍵字處理
5.檢查key value對應值(type,value)繼承

public class CommonObjectImpl<T,R> extends AssertBase implements AssertActionI<T,R> {
    
    @Override
    public boolean api_Assert(Assertinfo assertinfo, T request, R Response) {   
        Map<String, Object> actual = convertToMap(Response);
        Map<String, Object> expect = convertToMap(request);
        return AssertBase.compareCommon(actual,expect,assertinfo.getAssert_value());
    }

    @Override
    public boolean matchCheckType(Assertinfo assertinfo, T request, R Response) {
        return isJsonMapObject(Response);
    }
}

 

(3)如何調用?放入list, spring管理接口

用spring注入 
<util:list id="customAsserts" value-type="service.responsehandler.verify.CustomAssert">
        <ref bean="assertCommonObject"/>
        <ref bean="assertList"/>
    </util:list>
  @Resource(name = "customAsserts")
  public void setCustomAsserts(List<CustomAssert> customAsserts) {
        TestBase.customAsserts = customAsserts;
    }

        for(AssertActionI ass: assertList) {
            if(ass.matchCheckType(ai,actual,expect)){   //符合驗證類型就調用
                ass.api_Assert(ai,actual,expect);
            }
        }

 

(4)和testng Assert 相結合,繼承Assert

        /**
         * @param actual
         * @param expect
         * @param message
         * 當actual和expect不能轉換成map作對比的時候,調用testng原生的Asssert
         */
    static public void assertEquals(Object actual, Object expect, String message) {
        if (!assertMapEquals(actual, expect)) {
            Assert.assertEquals(actual, expect, message);
        }
    }

 

(5)擴展後的驗證點不少,怎麼優化調用?

關於每一個assert實現的驗證點以下:

public enum AssertActions{ 
EQUAL,CONTAINS,SIZE,ISEMPTY,KEY_VALUE,CONTAINS_KEY,CONTAINS_VALUE; }

用if else判斷是十分麻煩的,能夠用反射去調用驗證方法,只須要輸入驗證的type和一個統一的驗證方法

以action名做爲方法名,用反射調用

public static boolean getAction(Class<?> c, String act, Object response, Object assertValue) throws IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException {
        Object obj = c.newInstance();
        Method[] methods=c.getDeclaredMethods();
        for (EumAction.AssertActions e : EumAction.AssertActions.values()) {
            if(e.toString().equals(act.toString())){
                for(Method m:methods){
                    if(m.getName().contains(act.toString())){
                        Method method=c.getMethod(m.getName(), Object.class,Object.class);
                        boolean str2= (Boolean) method.invoke(obj, new Object[]{response,assertValue});
                        System.out.println(str2);
                        return str2;
                    }
                }
            }
        }
        Assert.fail("No assertAction: "+act +" in "+c.getSimpleName());
        return true;
    }
相關文章
相關標籤/搜索