Package com.intellij.testFramework

Source Code of com.intellij.testFramework.InspectionTestCase

/*
* Created by IntelliJ IDEA.
* User: max
* Date: Apr 11, 2002
* Time: 5:18:36 PM
* To change template for new class use
* Code Style | Class Templates options (Tools | IDE Options).
*/
package com.intellij.testFramework;

import com.intellij.analysis.AnalysisScope;
import com.intellij.codeInspection.GlobalInspectionTool;
import com.intellij.codeInspection.InspectionManager;
import com.intellij.codeInspection.LocalInspectionTool;
import com.intellij.codeInspection.deadCode.DeadCodeInspection;
import com.intellij.codeInspection.ex.*;
import com.intellij.codeInspection.reference.RefManagerImpl;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.ex.PathManagerEx;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.projectRoots.ProjectJdk;
import com.intellij.openapi.projectRoots.impl.JavaSdkImpl;
import com.intellij.openapi.roots.ContentEntry;
import com.intellij.openapi.roots.ModifiableRootModel;
import com.intellij.openapi.roots.ModuleRootManager;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.JDOMUtil;
import com.intellij.openapi.vfs.LocalFileSystem;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.pom.java.LanguageLevel;
import com.intellij.psi.PsiManager;
import org.jdom.Document;
import org.jdom.Element;
import org.jetbrains.annotations.NonNls;

import java.io.CharArrayReader;
import java.io.File;
import java.io.StreamTokenizer;
import java.util.ArrayList;

@SuppressWarnings({"HardCodedStringLiteral"})
public abstract class InspectionTestCase extends PsiTestCase {
  private static final Logger LOG = Logger.getInstance("#com.intellij.testFramework.InspectionTestCase");

  public InspectionManagerEx getManager() {
    return (InspectionManagerEx) InspectionManager.getInstance(myProject);
  }

  public void doTest(@NonNls String folderName, LocalInspectionTool tool) throws Exception {
    doTest(folderName, new LocalInspectionToolWrapper(tool));
  }
  public void doTest(@NonNls String folderName, GlobalInspectionTool tool) throws Exception {
    doTest(folderName, new GlobalInspectionToolWrapper(tool));
  }
  public void doTest(@NonNls String folderName, GlobalInspectionTool tool, boolean checkRange) throws Exception {
    doTest(folderName, new GlobalInspectionToolWrapper(tool), checkRange);
  }

  public void doTest(@NonNls String folderName, GlobalInspectionTool tool, boolean checkRange, boolean runDeadCodeFirst) throws Exception {
    doTest(folderName, new GlobalInspectionToolWrapper(tool), "java 1.4", checkRange, runDeadCodeFirst);
  }

  public void doTest(@NonNls String folderName, InspectionTool tool) throws Exception {
    doTest(folderName, tool, "java 1.4");
  }

  public void doTest(@NonNls String folderName, InspectionTool tool, final boolean checkRange) throws Exception {
    doTest(folderName, tool, "java 1.4", checkRange);
  }

  public void doTest(@NonNls String folderName, InspectionTool tool, @NonNls final String jdkName) throws Exception {
    doTest(folderName, tool, jdkName, false);
  }

  public void doTest(@NonNls String folderName, InspectionTool tool, @NonNls final String jdkName, boolean checkRange) throws Exception {
    doTest(folderName, tool, jdkName, checkRange, false);
  }

  public void doTest(@NonNls String folderName, InspectionTool tool, @NonNls final String jdkName, boolean checkRange, boolean runDeadCodeFirst) throws Exception {
    final String testDir = getTestDataPath() + "/" + folderName;
    runTool(testDir, jdkName, tool, runDeadCodeFirst);

    final Element root = new Element("problems");
    final Document doc = new Document(root);
    tool.updateContent()//e.g. dead code need check for reachables
    tool.exportResults(root);

    File file = new File(testDir + "/expected.xml");
    Document expectedDocument = JDOMUtil.loadDocument(file);

    compareWithExpected(expectedDocument, doc, checkRange);
  }

  protected void runTool(@NonNls final String testDir, @NonNls final String jdkName, final InspectionTool tool) {
    runTool(testDir, jdkName, tool, false);
  }

  protected void runTool(final String testDir, final String jdkName, final InspectionTool tool, boolean runDeadCodeFirst) {
    final VirtualFile[] sourceDir = new VirtualFile[1];
    ApplicationManager.getApplication().runWriteAction(new Runnable() {
      public void run() {
        try {
          setupRootModel(testDir, sourceDir, jdkName);
        } catch (Exception e) {
          LOG.error(e);
        }
      }
    });
    AnalysisScope scope = createAnalysisScope(sourceDir[0]);

    InspectionManagerEx inspectionManager = (InspectionManagerEx) InspectionManager.getInstance(myProject);
    final GlobalInspectionContextImpl globalContext = inspectionManager.createNewGlobalContext(true);
    globalContext.setCurrentScope(scope);

    if (runDeadCodeFirst) {
      runTool(new DeadCodeInspection(), scope, globalContext, inspectionManager);
    }
    runTool(tool, scope, globalContext, inspectionManager);
  }

  protected AnalysisScope createAnalysisScope(VirtualFile sourceDir) {
    PsiManager psiManager = PsiManager.getInstance(myProject);
    return new AnalysisScope(psiManager.findDirectory(sourceDir));
  }

  private static void runTool(final InspectionTool tool,
                              final AnalysisScope scope,
                              final GlobalInspectionContextImpl globalContext,
                              final InspectionManagerEx inspectionManager) {
    tool.initialize(globalContext);
    ((RefManagerImpl)globalContext.getRefManager()).initializeAnnotators();
    if (tool.isGraphNeeded()){
      ((RefManagerImpl)tool.getRefManager()).findAllDeclarations();
    }

    tool.runInspection(scope, inspectionManager);

    tool.queryExternalUsagesRequests(inspectionManager);

    do {
      globalContext.processSearchRequests();
    } while (tool.queryExternalUsagesRequests(inspectionManager));
  }

  protected void setupRootModel(final String testDir, final VirtualFile[] sourceDir, final String jdkName) {
    VirtualFile projectDir = LocalFileSystem.getInstance().refreshAndFindFileByIoFile(new File(testDir));
    assertNotNull(projectDir);
    sourceDir[0] = projectDir.findChild("src");
    if (sourceDir[0] == null) {
      sourceDir[0] = projectDir;
    }
    VirtualFile ext_src = LocalFileSystem.getInstance().refreshAndFindFileByIoFile(new File(testDir + "/ext_src"));
    final ModuleRootManager rootManager = ModuleRootManager.getInstance(myModule);
    final ModifiableRootModel rootModel = rootManager.getModifiableModel();
    rootModel.clear();
    // configure source and output path
    final ContentEntry contentEntry = rootModel.addContentEntry(projectDir);
    contentEntry.addSourceFolder(sourceDir[0], false);
    if (ext_src != null) {
      contentEntry.addSourceFolder(ext_src, false);
    }

    // IMPORTANT! The jdk must be obtained in a way it is obtained in the normal program!
    //ProjectJdkEx jdk = ProjectJdkTable.getInstance().getInternalJdk();
    ProjectJdk jdk;
    if ("java 1.5".equals(jdkName)) {
      jdk = JavaSdkImpl.getMockJdk15(jdkName);
      myPsiManager.setEffectiveLanguageLevel(LanguageLevel.JDK_1_5);
    }
    else {
      jdk = JavaSdkImpl.getMockJdk(jdkName);
    }

    rootModel.setJdk(jdk);

    rootModel.commit();
  }

  @NonNls
  protected String getTestDataPath() {
    return PathManagerEx.getTestDataPath()+"/inspection/";
  }

  protected static void compareWithExpected(Document expectedDoc, Document doc, boolean checkRange) throws Exception {
    ArrayList<Object> expectedProblems = new ArrayList<Object>(expectedDoc.getRootElement().getChildren("problem"));
    ArrayList<Object> reportedProblems = new ArrayList<Object>(doc.getRootElement().getChildren("problem"));

    Element[] expectedArrayed = expectedProblems.toArray(new Element[expectedProblems.size()]);
    boolean failed = false;

expected:
    for (Element expectedProblem : expectedArrayed) {
      Element[] reportedArrayed = reportedProblems.toArray(new Element[reportedProblems.size()]);
      for (Element reportedProblem : reportedArrayed) {
        if (compareProblemWithExpected(reportedProblem, expectedProblem, checkRange)) {
          expectedProblems.remove(expectedProblem);
          reportedProblems.remove(reportedProblem);
          continue expected;
        }
      }

      Document missing = new Document((Element)expectedProblem.clone());
      System.out.println("The following haven't been reported as expected: " + new String(JDOMUtil.printDocument(missing, "\n")));
      failed = true;
    }

    for (Object reportedProblem1 : reportedProblems) {
      Element reportedProblem = (Element)reportedProblem1;
      Document extra = new Document((Element)reportedProblem.clone());
      System.out.println("The following has been unexpectedly reported: " + new String(JDOMUtil.printDocument(extra, "\n")));
      failed = true;
    }

    assertFalse(failed);
  }

  private static boolean compareProblemWithExpected(Element reportedProblem, Element expectedProblem, boolean checkRange) throws Exception {
    if (!compareFiles(reportedProblem, expectedProblem)) return false;
    if (!compareLines(reportedProblem, expectedProblem)) return false;
    if (!compareDescriptions(reportedProblem, expectedProblem)) return false;
    if (checkRange && !compareTextRange(reportedProblem, expectedProblem)) return false;
    return true;
  }

  private static boolean compareTextRange(final Element reportedProblem, final Element expectedProblem) {
    Element reportedTextRange = reportedProblem.getChild("entry_point");
    if (reportedTextRange == null) return false;
    Element expectedTextRange = expectedProblem.getChild("entry_point");
    return Comparing.equal(reportedTextRange.getAttributeValue("TYPE"), expectedTextRange.getAttributeValue("TYPE")) &&
           Comparing.equal(reportedTextRange.getAttributeValue("FQNAME"), expectedTextRange.getAttributeValue("FQNAME"));
  }

  private static boolean compareDescriptions(Element reportedProblem, Element expectedProblem) throws Exception {
    String expectedDescription = expectedProblem.getChildText("description");
    String reportedDescription = reportedProblem.getChildText("description");
    if (expectedDescription.equals(reportedDescription)) return true;
   
    StreamTokenizer tokenizer = new StreamTokenizer(new CharArrayReader(expectedDescription.toCharArray()));
    tokenizer.quoteChar('\'');

    int idx = 0;
    while (tokenizer.nextToken() != StreamTokenizer.TT_EOF) {
      String word;
      if (tokenizer.sval != null) {
        word = tokenizer.sval;
      } else if (tokenizer.ttype == StreamTokenizer.TT_NUMBER) {
        word = Double.toString(tokenizer.nval);
      }
      else {
        continue;
      }

      idx = reportedDescription.indexOf(word, idx);
      if (idx == -1) return false;
      idx += word.length();
    }

    return true;
  }

  private static boolean compareLines(Element reportedProblem, Element expectedProblem) {
    return Comparing.equal(reportedProblem.getChildText("line"), expectedProblem.getChildText("line"));
  }

  private static boolean compareFiles(Element reportedProblem, Element expectedProblem) {
    String reportedFileName = reportedProblem.getChildText("file");
    File reportedFile = new File(reportedFileName);

    return Comparing.equal(reportedFile.getName(), expectedProblem.getChildText("file"));
  }
}
TOP

Related Classes of com.intellij.testFramework.InspectionTestCase

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.