All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.aspectj.org.eclipse.jdt.internal.core.dom.rewrite.imports.RemovedImportCommentReassigner Maven / Gradle / Ivy

Go to download

AspectJ tools most notably contains the AspectJ compiler (AJC). AJC applies aspects to Java classes during compilation, fully replacing Javac for plain Java classes and also compiling native AspectJ or annotation-based @AspectJ syntax. Furthermore, AJC can weave aspects into existing class files in a post-compile binary weaving step. This library is a superset of AspectJ weaver and hence also of AspectJ runtime.

There is a newer version: 1.9.22.1
Show newest version
/*******************************************************************************
 * Copyright (c) 2015 Google Inc and others.
 *
 * This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License 2.0
 * which accompanies this distribution, and is available at
 * https://www.eclipse.org/legal/epl-2.0/
 *
 * SPDX-License-Identifier: EPL-2.0
 *
 * Contributors:
 *     John Glassmyer  - import group sorting is broken - https://bugs.eclipse.org/430303
 *******************************************************************************/
package org.aspectj.org.eclipse.jdt.internal.core.dom.rewrite.imports;

import java.util.ArrayDeque;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Deque;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

/**
 * Reassigns comments associated with removed imports (those present before but not present
 * after the rewrite) to resultant imports (those present after the rewrite).
 * 

* Reassigns comments of removed single imports to the first (in iteration order) resultant * on-demand import having the same container name, if one exists. *

* Reassigns comments of removed on-demand imports to the first (in iteration order) resultant * single import having the same container name, if one exists. *

* Leaves unassigned any removed import comment not matching the above cases. */ final class RemovedImportCommentReassigner { private static Collection retainImportsWithComments(Collection imports) { Collection importsWithComments = new ArrayList(imports.size()); for (OriginalImportEntry currentImport : imports) { if (!currentImport.comments.isEmpty()) { importsWithComments.add(currentImport); } } return importsWithComments; } private static boolean hasFloatingComment(OriginalImportEntry nextAssignedImport) { for (ImportComment importComment : nextAssignedImport.comments) { if (importComment.succeedingLineDelimiters > 1) { return true; } } return false; } private final Collection originalImportsWithComments; RemovedImportCommentReassigner(List originalImports) { this.originalImportsWithComments = retainImportsWithComments(originalImports); } /** * Assigns comments of removed import entries (those in {@code originalImports} but not in * {@code resultantImports}) to resultant import entries. *

* Returns a map containing the resulting assignments, where each key is an element of * {@code resultantImports} and each value is a collection of comments reassigned to that * resultant import. */ Map> reassignComments(Collection resultantImports) { Map> importAssignments = assignRemovedImports(resultantImports); Map> commentAssignments = new HashMap>(); for (Map.Entry> importAssignment : importAssignments.entrySet()) { ImportEntry targetImport = importAssignment.getKey(); if (targetImport != null) { Deque assignedComments = new ArrayDeque(); Collection assignedImports = importAssignment.getValue(); Iterator nextAssignedImportIterator = assignedImports.iterator(); if (nextAssignedImportIterator.hasNext()) { nextAssignedImportIterator.next(); } Iterator assignedImportIterator = assignedImports.iterator(); while (assignedImportIterator.hasNext()) { OriginalImportEntry currentAssignedImport = assignedImportIterator.next(); OriginalImportEntry nextAssignedImport = nextAssignedImportIterator.hasNext() ? nextAssignedImportIterator.next() : null; assignedComments.addAll(currentAssignedImport.comments); if (nextAssignedImport != null && hasFloatingComment(nextAssignedImport)) { // Ensure that a blank line separates this removed import's comments // from the next removed import's floating comments. ImportComment lastComment = assignedComments.removeLast(); ImportComment lastCommentWithTrailingBlankLine = new ImportComment(lastComment.region, 2); assignedComments.add(lastCommentWithTrailingBlankLine); } } commentAssignments.put(targetImport, assignedComments); } } return commentAssignments; } private Map> assignRemovedImports(Collection imports) { Collection removedImportsWithComments = identifyRemovedImportsWithComments(imports); if (removedImportsWithComments.isEmpty()) { return Collections.emptyMap(); } Map firstSingleForOnDemand = identifyFirstSingleForEachOnDemand(imports); Map firstOccurrences = identifyFirstOccurrenceOfEachImportName(imports); Map> removedImportsForRetainedImport = new HashMap>(); for (ImportEntry retainedImport : imports) { removedImportsForRetainedImport.put(retainedImport, new ArrayList()); } // The null key will map to the removed imports not assigned to any import. removedImportsForRetainedImport.put(null, new ArrayList()); for (OriginalImportEntry removedImport : removedImportsWithComments) { ImportName removedImportName = removedImport.importName; final ImportEntry retainedImport; if (removedImportName.isOnDemand()) { retainedImport = firstSingleForOnDemand.get(removedImportName); } else { retainedImport = firstOccurrences.get(removedImportName.getContainerOnDemand()); } // retainedImport will be null if there's no corresponding import to which to assign the removed import. removedImportsForRetainedImport.get(retainedImport).add(removedImport); } return removedImportsForRetainedImport; } private Collection identifyRemovedImportsWithComments(Collection imports) { Collection removedImports = new ArrayList(this.originalImportsWithComments); removedImports.removeAll(imports); return removedImports; } /** * Assigns each removed on-demand import to the first single import in {@code imports} having * the same container name. *

* Returns a map where each key is a single import and each value is the corresponding * removed on-demand import. *

* The returned map only contains mappings to removed on-demand imports for which there are * corresponding single imports in {@code imports}. */ private Map identifyFirstSingleForEachOnDemand(Iterable imports) { Map firstSingleImportForContainer = new HashMap(); for (ImportEntry currentImport : imports) { if (!currentImport.importName.isOnDemand()) { ImportName containerOnDemand = currentImport.importName.getContainerOnDemand(); if (!firstSingleImportForContainer.containsKey(containerOnDemand)) { firstSingleImportForContainer.put(containerOnDemand, currentImport); } } } return firstSingleImportForContainer; } private Map identifyFirstOccurrenceOfEachImportName(Iterable imports) { Map firstOccurrenceOfImport = new HashMap(); for (ImportEntry resultantImport : imports) { if (!firstOccurrenceOfImport.containsKey(resultantImport.importName)) { firstOccurrenceOfImport.put(resultantImport.importName, resultantImport); } } return firstOccurrenceOfImport; } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy