@Override public void computeUsages(List<PsiLiteralExpression> targets) { final Project project = myTarget.getProject(); final PsiElement parent = myTarget.getParent().getParent(); final LocalInspectionsPass pass = new LocalInspectionsPass( myFile, myFile.getViewProvider().getDocument(), parent.getTextRange().getStartOffset(), parent.getTextRange().getEndOffset(), LocalInspectionsPass.EMPTY_PRIORITY_RANGE, false, HighlightInfoProcessor.getEmpty()); final InspectionProfile inspectionProfile = InspectionProjectProfileManager.getInstance(project).getInspectionProfile(); for (PsiLiteralExpression target : targets) { final Object value = target.getValue(); if (!(value instanceof String)) { continue; } InspectionToolWrapper toolWrapperById = ((InspectionProfileImpl) inspectionProfile).getToolById((String) value, target); if (!(toolWrapperById instanceof LocalInspectionToolWrapper)) { continue; } final LocalInspectionToolWrapper toolWrapper = ((LocalInspectionToolWrapper) toolWrapperById).createCopy(); final InspectionManagerEx managerEx = (InspectionManagerEx) InspectionManager.getInstance(project); final GlobalInspectionContextImpl context = managerEx.createNewGlobalContext(false); toolWrapper.initialize(context); ((RefManagerImpl) context.getRefManager()).inspectionReadActionStarted(); ProgressIndicator indicator = ProgressManager.getInstance().getProgressIndicator(); Runnable inspect = new Runnable() { @Override public void run() { pass.doInspectInBatch( context, managerEx, Collections.<LocalInspectionToolWrapper>singletonList(toolWrapper)); } }; if (indicator == null) { ProgressManager.getInstance() .executeProcessUnderProgress(inspect, new ProgressIndicatorBase()); } else { inspect.run(); } for (HighlightInfo info : pass.getInfos()) { final PsiElement element = CollectHighlightsUtil.findCommonParent(myFile, info.startOffset, info.endOffset); if (element != null) { addOccurrence(element); } } } }
private void checkRequiredAttributes( XmlTag tag, String name, XmlElementDescriptor elementDescriptor) { XmlAttributeDescriptor[] attributeDescriptors = elementDescriptor.getAttributesDescriptors(tag); Set<String> requiredAttributes = null; for (XmlAttributeDescriptor attribute : attributeDescriptors) { if (attribute != null && attribute.isRequired()) { if (requiredAttributes == null) { requiredAttributes = new HashSet<String>(); } requiredAttributes.add(attribute.getName(tag)); } } if (requiredAttributes != null) { for (final String attrName : requiredAttributes) { if (tag.getAttribute(attrName, "") == null && !XmlExtension.getExtension(tag.getContainingFile()) .isRequiredAttributeImplicitlyPresent(tag, attrName)) { final InsertRequiredAttributeFix insertRequiredAttributeIntention = new InsertRequiredAttributeFix(tag, attrName, null); final String localizedMessage = XmlErrorMessages.message("element.doesnt.have.required.attribute", name, attrName); final InspectionProfile profile = InspectionProjectProfileManager.getInstance(tag.getProject()).getInspectionProfile(); final LocalInspectionToolWrapper toolWrapper = (LocalInspectionToolWrapper) profile.getInspectionTool(RequiredAttributesInspection.SHORT_NAME, tag); if (toolWrapper != null) { RequiredAttributesInspection inspection = (RequiredAttributesInspection) toolWrapper.getTool(); reportOneTagProblem( tag, attrName, localizedMessage, insertRequiredAttributeIntention, HighlightDisplayKey.find(RequiredAttributesInspection.SHORT_NAME), inspection, XmlEntitiesInspection.NOT_REQUIRED_ATTRIBUTE); } } } } }
private static ProblemDescriptor runLocalTool( @NotNull PsiElement psiElement, @NotNull InspectionManager inspectionManager, @NotNull OfflineProblemDescriptor offlineProblemDescriptor, @NotNull LocalInspectionToolWrapper toolWrapper) { PsiFile containingFile = psiElement.getContainingFile(); final ProblemsHolder holder = new ProblemsHolder(inspectionManager, containingFile, false); final LocalInspectionTool localTool = toolWrapper.getTool(); final int startOffset = psiElement.getTextRange().getStartOffset(); final int endOffset = psiElement.getTextRange().getEndOffset(); LocalInspectionToolSession session = new LocalInspectionToolSession(containingFile, startOffset, endOffset); final PsiElementVisitor visitor = localTool.buildVisitor(holder, false, session); localTool.inspectionStarted(session, false); final PsiElement[] elementsInRange = getElementsIntersectingRange(containingFile, startOffset, endOffset); for (PsiElement element : elementsInRange) { element.accept(visitor); } localTool.inspectionFinished(session, holder); if (holder.hasResults()) { final List<ProblemDescriptor> list = holder.getResults(); final int idx = offlineProblemDescriptor.getProblemIndex(); int curIdx = 0; for (ProblemDescriptor descriptor : list) { final PsiNamedElement member = localTool.getProblemElement(descriptor.getPsiElement()); if (psiElement instanceof PsiFile || member != null && member.equals(psiElement)) { if (curIdx == idx) { return descriptor; } curIdx++; } } } return null; }
public CommonProblemDescriptor[] checkElement( @NotNull final PsiElement psiElement, InspectionManager manager, Project project) { final Map<PsiElement, Collection<String>> suppressedScopes = new THashMap<PsiElement, Collection<String>>(); psiElement.accept( new JavaRecursiveElementWalkingVisitor() { @Override public void visitModifierList(PsiModifierList list) { super.visitModifierList(list); final PsiElement parent = list.getParent(); if (parent instanceof PsiModifierListOwner && !(parent instanceof PsiClass)) { checkElement(parent); } } @Override public void visitComment(PsiComment comment) { checkElement(comment); } @Override public void visitClass(PsiClass aClass) { if (aClass == psiElement) { super.visitClass(aClass); checkElement(aClass); } } private void checkElement(final PsiElement owner) { String idsString = SuppressManager.getInstance().getSuppressedInspectionIdsIn(owner); if (idsString != null && idsString.length() != 0) { List<String> ids = StringUtil.split(idsString, ","); if (IGNORE_ALL && (ids.contains(SuppressionUtil.ALL) || ids.contains(SuppressionUtil.ALL.toLowerCase()))) return; Collection<String> suppressed = suppressedScopes.get(owner); if (suppressed == null) { suppressed = ids; } else { for (String id : ids) { if (!suppressed.contains(id)) { suppressed.add(id); } } } suppressedScopes.put(owner, suppressed); } } }); if (suppressedScopes.values().isEmpty()) return null; // have to visit all file from scratch since inspections can be written in any perversive way // including checkFile() overriding Collection<InspectionTool> suppressedTools = new THashSet<InspectionTool>(); InspectionTool[] tools = getInspectionTools(psiElement, manager); for (Collection<String> ids : suppressedScopes.values()) { for (Iterator<String> iterator = ids.iterator(); iterator.hasNext(); ) { final String shortName = iterator.next().trim(); for (InspectionTool tool : tools) { if (tool instanceof LocalInspectionToolWrapper && ((LocalInspectionToolWrapper) tool).getTool().getID().equals(shortName)) { if (!((LocalInspectionToolWrapper) tool).isUnfair()) { suppressedTools.add(tool); } else { iterator.remove(); break; } } else if (tool.getShortName().equals(shortName)) { // ignore global unused as it won't be checked anyway if (!(tool instanceof LocalInspectionToolWrapper) && !(tool instanceof GlobalInspectionToolWrapper)) { iterator.remove(); break; } else { suppressedTools.add(tool); } } } } } final AnalysisScope scope = new AnalysisScope(psiElement.getContainingFile()); final InspectionManagerEx inspectionManagerEx = ((InspectionManagerEx) InspectionManager.getInstance(project)); GlobalInspectionContextImpl globalContext = inspectionManagerEx.createNewGlobalContext(false); globalContext.setCurrentScope(scope); final RefManagerImpl refManager = ((RefManagerImpl) globalContext.getRefManager()); refManager.inspectionReadActionStarted(); final List<ProblemDescriptor> result; try { result = new ArrayList<ProblemDescriptor>(); for (InspectionTool tool : suppressedTools) { String toolId = tool instanceof LocalInspectionToolWrapper ? ((LocalInspectionToolWrapper) tool).getTool().getID() : tool.getShortName(); tool.initialize(globalContext); Collection<CommonProblemDescriptor> descriptors; if (tool instanceof LocalInspectionToolWrapper) { LocalInspectionToolWrapper local = (LocalInspectionToolWrapper) tool; if (local.isUnfair()) continue; // cant't work with passes other than LocalInspectionPass local.processFile(psiElement.getContainingFile(), false, manager); descriptors = local.getProblemDescriptors(); } else if (tool instanceof GlobalInspectionToolWrapper) { GlobalInspectionToolWrapper global = (GlobalInspectionToolWrapper) tool; if (global.getTool().isGraphNeeded()) { refManager.findAllDeclarations(); } global.processFile(scope, manager, globalContext, false); descriptors = global.getProblemDescriptors(); } else { continue; } for (PsiElement suppressedScope : suppressedScopes.keySet()) { Collection<String> suppressedIds = suppressedScopes.get(suppressedScope); if (!suppressedIds.contains(toolId)) continue; for (CommonProblemDescriptor descriptor : descriptors) { if (!(descriptor instanceof ProblemDescriptor)) continue; PsiElement element = ((ProblemDescriptor) descriptor).getPsiElement(); if (element == null) continue; PsiElement annotation = SuppressManager.getInstance().getElementToolSuppressedIn(element, toolId); if (annotation != null && PsiTreeUtil.isAncestor(suppressedScope, annotation, false) || annotation == null && !PsiTreeUtil.isAncestor(suppressedScope, element, false)) { suppressedIds.remove(toolId); break; } } } } for (PsiElement suppressedScope : suppressedScopes.keySet()) { Collection<String> suppressedIds = suppressedScopes.get(suppressedScope); for (String toolId : suppressedIds) { PsiMember psiMember; String problemLine = null; if (suppressedScope instanceof PsiMember) { psiMember = (PsiMember) suppressedScope; } else { psiMember = PsiTreeUtil.getParentOfType(suppressedScope, PsiDocCommentOwner.class); final PsiStatement statement = PsiTreeUtil.getNextSiblingOfType(suppressedScope, PsiStatement.class); problemLine = statement != null ? statement.getText() : null; } if (psiMember != null && psiMember.isValid()) { String description = InspectionsBundle.message("inspection.redundant.suppression.description"); if (myQuickFixes == null) myQuickFixes = new BidirectionalMap<String, QuickFix>(); final String key = toolId + (problemLine != null ? ";" + problemLine : ""); QuickFix fix = myQuickFixes.get(key); if (fix == null) { fix = new RemoveSuppressWarningAction(toolId, problemLine); myQuickFixes.put(key, fix); } PsiElement identifier = null; if (psiMember instanceof PsiMethod) { identifier = ((PsiMethod) psiMember).getNameIdentifier(); } else if (psiMember instanceof PsiField) { identifier = ((PsiField) psiMember).getNameIdentifier(); } else if (psiMember instanceof PsiClass) { identifier = ((PsiClass) psiMember).getNameIdentifier(); } if (identifier == null) { identifier = psiMember; } result.add( manager.createProblemDescriptor( identifier, description, (LocalQuickFix) fix, ProblemHighlightType.GENERIC_ERROR_OR_WARNING, false)); } } } } finally { refManager.inspectionReadActionFinished(); globalContext.close(true); } return result.toArray(new ProblemDescriptor[result.size()]); }