/testability-explorer/src/test/java/com/google/test/metric/TestabilityVisitorTest.java

http://testability-explorer.googlecode.com/ · Java · 238 lines · 189 code · 34 blank · 15 comment · 3 complexity · dca66375066de8067c3c502da8a73ae4 MD5 · raw file

  1. /*
  2. * Copyright 2007 Google Inc.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License"); you may not
  5. * use this file except in compliance with the License. You may obtain a copy of
  6. * the License at
  7. *
  8. * http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
  12. * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
  13. * License for the specific language governing permissions and limitations under
  14. * the License.
  15. */
  16. package com.google.test.metric;
  17. import static java.util.Collections.EMPTY_LIST;
  18. import java.util.ArrayList;
  19. import java.util.Arrays;
  20. import java.util.List;
  21. import junit.framework.TestCase;
  22. import com.google.test.metric.TestabilityVisitor.CostRecordingFrame;
  23. import com.google.test.metric.TestabilityVisitor.ParentFrame;
  24. public class TestabilityVisitorTest extends TestCase {
  25. final List<Integer> cost1 = Arrays.asList(0);
  26. Variable instance = new Variable("instance", null, false, false);
  27. Variable finalInstance = new Variable("instance", null, true, false);
  28. FieldInfo field = new FieldInfo(null, "field", null, false, false, false);
  29. FieldInfo finalField = new FieldInfo(null, "field", null, true, false, false);
  30. FieldInfo finalStaticField = new FieldInfo(null, "field", null, true, true, false);
  31. LocalField localField = new LocalField(instance, field);
  32. LocalField localFinalField = new LocalField(instance, finalField);
  33. LocalField localStaticFinalField = new LocalField(null, finalStaticField);
  34. Variable dst = new Variable("dst", null, false, false);
  35. Variable dstField = new FieldInfo(null, "dstField", null, false, false, false);
  36. @SuppressWarnings("unchecked")
  37. ClassInfo classInfo = new ClassInfo("c.g.t.A", false, null, EMPTY_LIST, null);
  38. MethodInfo method =
  39. new MethodInfo(classInfo, "void method()", 0, null, null, null, null, null, false, false, cost1);
  40. private final JavaClassRepository repo = new JavaClassRepository();
  41. private final VariableState globalVariables = new VariableState();
  42. TestabilityVisitor visitor =
  43. new TestabilityVisitor(repo, globalVariables, null, new RegExpWhiteList());
  44. TestabilityVisitor.CostRecordingFrame frame = visitor.createFrame(method, 1);
  45. ParentFrame parentFrame = frame.getParentFrame();
  46. private String method(String string, Class<?> clazz) {
  47. return "void execute("+clazz.getName()+")";
  48. }
  49. public void testIsInjectable() throws Exception {
  50. Variable var = new Variable("", JavaType.fromJava("X"), false, false);
  51. assertFalse(globalVariables.isInjectable(var));
  52. globalVariables.setInjectable(var);
  53. assertTrue(globalVariables.isInjectable(var));
  54. }
  55. public void testNoop() throws Exception {
  56. frame.assignParameter(1, dst, parentFrame, instance);
  57. assertFalse(globalVariables.isGlobal(dst));
  58. assertFalse(globalVariables.isInjectable(dst));
  59. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  60. }
  61. public void testInjectability() throws Exception {
  62. globalVariables.setInjectable(instance);
  63. frame.assignParameter(1, dst, parentFrame, instance);
  64. assertFalse(globalVariables.isGlobal(dst));
  65. assertTrue(frame.getVariableState().isInjectable(dst));
  66. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  67. }
  68. public void testFieldReadNoop() throws Exception {
  69. frame.assignParameter(1, dst, parentFrame, localField);
  70. assertFalse(globalVariables.isGlobal(dst));
  71. assertFalse(globalVariables.isInjectable(dst));
  72. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  73. }
  74. public void testFieldReadInjectableInstance() throws Exception {
  75. globalVariables.setInjectable(instance);
  76. frame.assignParameter(1, dst, parentFrame, localField);
  77. assertFalse(globalVariables.isGlobal(dst));
  78. assertFalse(globalVariables.isInjectable(dst));
  79. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  80. }
  81. public void testFieldReadInjectableField() throws Exception {
  82. globalVariables.setInjectable(field);
  83. frame.assignParameter(1, dst, parentFrame, localField);
  84. assertFalse(globalVariables.isGlobal(dst));
  85. assertTrue(frame.getVariableState().isInjectable(dst));
  86. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  87. }
  88. public void testFieldReadGlobalInstance() throws Exception {
  89. globalVariables.setGlobal(instance);
  90. frame.assignParameter(1, dstField, parentFrame, localField);
  91. assertTrue(globalVariables.isGlobal(dstField));
  92. assertFalse(globalVariables.isInjectable(dstField));
  93. assertEquals(1, frame.getMethodCost().getTotalCost().getGlobalCost());
  94. }
  95. public void testFinalFieldReadGlobalInstance() throws Exception {
  96. globalVariables.setGlobal(instance);
  97. frame.assignParameter(1, dstField, parentFrame, localFinalField);
  98. assertTrue(globalVariables.isGlobal(dstField));
  99. assertFalse(globalVariables.isInjectable(dstField));
  100. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  101. }
  102. public void testReadFinalStaticField() throws Exception {
  103. frame.assignParameter(1, dstField, parentFrame, localStaticFinalField);
  104. assertTrue(globalVariables.isGlobal(dstField));
  105. assertFalse(globalVariables.isInjectable(dstField));
  106. assertEquals(0, frame.getMethodCost().getTotalCost().getGlobalCost());
  107. }
  108. private static class LoDExample {
  109. Object conforming;
  110. Object violator;
  111. Object transitiveViolator;
  112. public void assign(Object in) {
  113. conforming = in;
  114. violator = in.getClass();
  115. transitiveViolator = violator;
  116. }
  117. }
  118. public void testLoDExample() throws Exception {
  119. ClassInfo clazz = repo.getClass(LoDExample.class.getCanonicalName());
  120. MethodInfo methodInfo = clazz.getMethod("void assign(java.lang.Object)");
  121. CostRecordingFrame frame = visitor.createFrame(methodInfo, 1);
  122. frame.applyMethodOperations();
  123. assertEquals(0, frame.getLoDCount(clazz.getField("conforming")));
  124. assertEquals(1, frame.getLoDCount(clazz.getField("violator")));
  125. assertEquals(1, frame.getLoDCount(clazz.getField("transitiveViolator")));
  126. }
  127. private static class LoDMultipleSameInvocations {
  128. Obj plus2;
  129. public void execute(Obj plus0) {
  130. Obj plus1 = plus0.getValueA();
  131. plus2 = plus1.getValueA();
  132. plus2 = plus1;
  133. }
  134. }
  135. public void testLoDMultipleSameInvocations() throws Exception {
  136. ClassInfo clazz = repo.getClass(LoDMultipleSameInvocations.class.getCanonicalName());
  137. MethodInfo methodInfo = clazz.getMethod(method("execute", Obj.class));
  138. CostRecordingFrame frame = visitor.createFrame(methodInfo, 1);
  139. frame.applyMethodOperations();
  140. assertEquals(2, frame.getLoDCount(clazz.getField("plus2")));
  141. }
  142. private static class LoDMultipleDifferentInvocations {
  143. Obj plus2;
  144. public void execute(Obj plus0) {
  145. Obj plus1 = plus0.getValueA();
  146. plus2 = plus1.getValueB();
  147. plus2 = plus1;
  148. }
  149. }
  150. public void testLoDMultipleDifferentInvocations() throws Exception {
  151. ClassInfo clazz = repo.getClass(LoDMultipleDifferentInvocations.class.getCanonicalName());
  152. MethodInfo methodInfo = clazz.getMethod(method("execute", Obj.class));
  153. CostRecordingFrame frame = visitor.createFrame(methodInfo, 1);
  154. frame.applyMethodOperations();
  155. assertEquals(2, frame.getLoDCount(clazz.getField("plus2")));
  156. MethodCost methodCost = frame.getMethodCost();
  157. List<LoDViolation> costSources = filterLoD(methodCost.getViolationCosts());
  158. assertEquals(1, costSources.size());
  159. LoDViolation violation = costSources.get(0);
  160. assertTrue(violation.getDescription().contains("getValueB()"));
  161. assertTrue(violation.getDescription().contains("[distance=2]"));
  162. }
  163. private List<LoDViolation> filterLoD(List<? extends ViolationCost> violations) {
  164. List<LoDViolation> lods = new ArrayList<LoDViolation>();
  165. for (ViolationCost violation : violations) {
  166. if (violation instanceof LoDViolation) {
  167. lods.add((LoDViolation) violation);
  168. }
  169. }
  170. return lods;
  171. }
  172. private static class MultipleInjectability {
  173. private Obj injectable1;
  174. private Obj injectable2;
  175. public void execute(Obj injectable) {
  176. injectable1 = injectable.getValueA();
  177. injectable2 = injectable.getValueA();
  178. }
  179. public boolean useFields() {
  180. return injectable1 == injectable2;
  181. }
  182. }
  183. public void testMultipleInjectability() throws Exception {
  184. ClassInfo clazz = repo.getClass(MultipleInjectability.class.getCanonicalName());
  185. MethodInfo methodInfo = clazz.getMethod(method("execute", Obj.class));
  186. globalVariables.setInjectable(methodInfo.getParameters().get(0));
  187. visitor.createFrame(methodInfo, 1).applyMethodOperations();
  188. assertTrue(frame.getVariableState().isInjectable(clazz.getField("injectable1")));
  189. assertTrue(frame.getVariableState().isInjectable(clazz.getField("injectable2")));
  190. }
  191. private static class LoDStaticCall {
  192. Obj plus1;
  193. public void execute() {
  194. plus1 = Obj.getStaticValueA();
  195. }
  196. }
  197. public void testLoDStaticCall() throws Exception {
  198. ClassInfo clazz = repo.getClass(LoDStaticCall.class.getCanonicalName());
  199. MethodInfo methodInfo = clazz.getMethod("void execute()");
  200. CostRecordingFrame frame = visitor.createFrame(methodInfo, 1);
  201. frame.applyMethodOperations();
  202. assertEquals(1, frame.getLoDCount(clazz.getField("plus1")));
  203. }
  204. }