org.eclipse.ajdt.core.AspectJCore.java Source code

Java tutorial

Introduction

Here is the source code for org.eclipse.ajdt.core.AspectJCore.java

Source

/*******************************************************************************
 * Copyright (c) 2005 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials 
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *     Matt Chapman - initial version
 *******************************************************************************/
package org.eclipse.ajdt.core;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.eclipse.ajdt.core.codeconversion.AspectsConvertingParser;
import org.eclipse.ajdt.core.javaelements.AJCodeElement;
import org.eclipse.ajdt.core.javaelements.AJCompilationUnit;
import org.eclipse.ajdt.core.javaelements.AJCompilationUnitManager;
import org.eclipse.ajdt.core.javaelements.AJInjarElement;
import org.eclipse.ajdt.core.javaelements.AspectElement;
import org.eclipse.ajdt.core.javaelements.BinaryAspectElement;
import org.eclipse.ajdt.internal.core.AJWorkingCopyOwner;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IResource;
import org.eclipse.jdt.core.IJavaElement;
import org.eclipse.jdt.core.IOpenable;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.WorkingCopyOwner;
import org.eclipse.jdt.internal.core.ClassFile;
import org.eclipse.jdt.internal.core.DefaultWorkingCopyOwner;
import org.eclipse.jdt.internal.core.JavaElement;
import org.eclipse.jdt.internal.core.JavaModelManager;
import org.eclipse.jdt.internal.core.PackageFragment;

public class AspectJCore {

    public static IJavaElement create(IFile file) {
        if ("aj".equals(file.getFileExtension())) {
            return AJCompilationUnitManager.INSTANCE.getAJCompilationUnit(file);
        }
        return JavaModelManager.create(file, null/*unknown java project*/);
    }

    /**
     * Returns the Java model element corresponding to the given handle
     * identifier generated by <code>IJavaElement.getHandleIdentifier()</code>,
     * or <code>null</code> if unable to create the associated element.
     * 
     * @param handleIdentifier
     *            the given handle identifier
     * @return the Java element corresponding to the handle identifier
     */
    public static IJavaElement create(String handleIdentifier) {
        return create(handleIdentifier, AJWorkingCopyOwner.INSTANCE);
    }

    private static int indexOfIgnoringEscapes(String str, char ch) {
        boolean prevEscape = false;
        for (int i = 0; i < str.length(); i++) {
            char c = str.charAt(i);
            if (c == JavaElement.JEM_ESCAPE) {
                prevEscape = true;
            } else {
                if ((c == ch) && (!prevEscape)) {
                    return i;
                }
                prevEscape = false;
            }
        }
        return -1;
    }

    private static IJavaElement getCodeElement(String codeElementHandle, JavaElement parent) {
        int li = indexOfIgnoringEscapes(codeElementHandle, JavaElement.JEM_COUNT);
        if (li != -1) {
            int occurrenceIndex = codeElementHandle.lastIndexOf(JavaElement.JEM_COUNT);
            if (Character.isDigit(codeElementHandle.charAt(occurrenceIndex + 1))) {
                int occurrence = Integer.parseInt(codeElementHandle.substring(occurrenceIndex + 1));
                String cname = codeElementHandle.substring(0, li);
                return new AJCodeElement(parent, cname, occurrence);
            }
            codeElementHandle = codeElementHandle.substring(0, li);
        }
        // no occurrance count
        return new AJCodeElement(parent, codeElementHandle);
    }

    public static IJavaElement create(String handleIdentifier, WorkingCopyOwner owner) {

        if (handleIdentifier == null) {
            return null;
        }
        Map aspectsInJavaFiles = new HashMap();

        boolean isCodeElement = false;
        String codeElementHandle = ""; //$NON-NLS-1$

        int codeElementDelimPos = indexOfIgnoringEscapes(handleIdentifier, AspectElement.JEM_CODEELEMENT);
        if (codeElementDelimPos != -1) {
            isCodeElement = true;
            codeElementHandle = handleIdentifier.substring(codeElementDelimPos + 1);
            handleIdentifier = handleIdentifier.substring(0, codeElementDelimPos);
        }

        AJMementoTokenizer memento = new AJMementoTokenizer(handleIdentifier);
        while (memento.hasMoreTokens()) {
            String token = memento.nextToken();
            if ((token.charAt(0) == AspectElement.JEM_ASPECT_CU)
                    || (token.charAt(0) == JavaElement.JEM_COMPILATIONUNIT)
                    || (token.charAt(0) == JavaElement.JEM_CLASSFILE)) {

                int index;
                if (token.charAt(0) == AspectElement.JEM_ASPECT_CU) {
                    index = handleIdentifier.indexOf(AspectElement.JEM_ASPECT_CU);
                } else if (token.charAt(0) == JavaElement.JEM_COMPILATIONUNIT) {
                    index = handleIdentifier.indexOf(JavaElement.JEM_COMPILATIONUNIT);
                } else { // JEM_CLASSFILE 
                    index = handleIdentifier.indexOf(JavaElement.JEM_CLASSFILE);
                }

                if (index != -1) {
                    IJavaElement je = JavaCore.create(handleIdentifier.substring(0, index));
                    if (je instanceof PackageFragment) {
                        PackageFragment pf = (PackageFragment) je;
                        String cuName = handleIdentifier.substring(index + 1);
                        int ind1 = cuName.indexOf(JavaElement.JEM_TYPE);
                        if (ind1 != -1) {
                            cuName = cuName.substring(0, ind1);
                        }
                        int ind2 = cuName.indexOf(AspectElement.JEM_ASPECT_TYPE);
                        if (ind2 != -1) {
                            cuName = cuName.substring(0, ind2);
                        }
                        int ind3 = cuName.indexOf(AspectElement.JEM_ITD_METHOD);
                        if (ind3 != -1) {
                            cuName = cuName.substring(0, ind3);
                        }
                        ind3 = cuName.indexOf(AspectElement.JEM_ITD_FIELD);
                        if (ind3 != -1) {
                            cuName = cuName.substring(0, ind3);
                        }
                        int ind4 = cuName.indexOf(AspectElement.JEM_DECLARE);
                        if (ind4 != -1) {
                            cuName = cuName.substring(0, ind4);
                        }
                        int ind5 = cuName.indexOf(AspectElement.JEM_IMPORTDECLARATION);
                        if (ind5 != -1) {
                            cuName = cuName.substring(0, ind5);
                        }
                        int ind6 = cuName.indexOf(AspectElement.JEM_PACKAGEDECLARATION);
                        if (ind6 != -1) {
                            cuName = cuName.substring(0, ind6);
                        }
                        if (CoreUtils.ASPECTJ_SOURCE_ONLY_FILTER.accept(cuName)) {
                            // no need to use a cuprovider because we know this
                            // is an AJCompilationUnit
                            JavaElement cu = new AJCompilationUnit(pf, cuName, owner);
                            token = memento.nextToken();
                            if (!memento.hasMoreTokens()) {
                                return cu;
                            }
                            IJavaElement restEl = cu.getHandleFromMemento(memento.nextToken(), memento, owner);
                            if (restEl != null) {
                                if (isCodeElement) {
                                    // there was an AJCodeElement at the end of
                                    // the handle
                                    IJavaElement codeEl = getCodeElement(codeElementHandle, (JavaElement) restEl);
                                    if (codeEl != null) {
                                        return codeEl;
                                    }
                                }
                                return restEl;
                            }
                        } else {
                            // Use the default working copy owner for Java elements
                            IJavaElement restEl = pf.getHandleFromMemento(token, memento,
                                    DefaultWorkingCopyOwner.PRIMARY);
                            if (restEl != null) {
                                if (isCodeElement) {
                                    // there was an AJCodeElement at the end of
                                    // the handle
                                    IJavaElement codeEl = getCodeElement(codeElementHandle, (JavaElement) restEl);
                                    if (codeEl != null) {
                                        return codeEl;
                                    }
                                }
                                return restEl;
                            } else if (ind2 != -1) { // An aspect in a .java file...
                                int index3 = handleIdentifier.indexOf(AspectElement.JEM_ASPECT_TYPE);
                                String aspectName = handleIdentifier.substring(index3 + 1);
                                boolean identifierIsAspect = true;
                                int ind7 = aspectName.indexOf(AspectElement.JEM_DECLARE);
                                if (ind7 != -1) {
                                    aspectName = aspectName.substring(0, ind7);
                                    identifierIsAspect = false;
                                }
                                int ind8 = aspectName.indexOf(AspectElement.JEM_ADVICE);
                                if (ind8 != -1) {
                                    aspectName = aspectName.substring(0, ind8);
                                    identifierIsAspect = false;
                                }
                                int ind9 = aspectName.indexOf(AspectElement.JEM_ITD_METHOD);
                                if (ind9 != -1) {
                                    aspectName = aspectName.substring(0, ind9);
                                    identifierIsAspect = false;
                                }
                                ind9 = aspectName.indexOf(AspectElement.JEM_ITD_FIELD);
                                if (ind9 != -1) {
                                    aspectName = aspectName.substring(0, ind9);
                                    identifierIsAspect = false;
                                }
                                int ind10 = aspectName.indexOf(AspectElement.JEM_ASPECT_TYPE);
                                if (ind10 != -1) {
                                    aspectName = aspectName.substring(0, ind10);
                                    identifierIsAspect = false;
                                }
                                int ind11 = aspectName.indexOf(AspectElement.JEM_TYPE);
                                if (ind11 != -1) {
                                    aspectName = aspectName.substring(0, ind11);
                                    identifierIsAspect = false;
                                }
                                int ind12 = aspectName.indexOf(AspectElement.JEM_FIELD);
                                if (ind12 != -1) {
                                    aspectName = aspectName.substring(0, ind12);
                                    identifierIsAspect = false;
                                }
                                int ind13 = aspectName.indexOf(AspectElement.JEM_METHOD);
                                if (ind13 != -1) {
                                    aspectName = aspectName.substring(0, ind13);
                                    identifierIsAspect = false;
                                }
                                int ind14 = aspectName.indexOf(AspectElement.JEM_POINTCUT);
                                if (ind14 != -1) {
                                    aspectName = aspectName.substring(0, ind14);
                                    identifierIsAspect = false;
                                }
                                IOpenable openable;
                                if (cuName.endsWith(".class")) {
                                    openable = pf.getClassFile(cuName);
                                } else {
                                    openable = pf.getCompilationUnit(cuName);
                                }
                                List l;
                                if (aspectsInJavaFiles.get(openable) instanceof List) {
                                    l = (List) aspectsInJavaFiles.get(openable);
                                } else {
                                    l = new ArrayList();
                                    aspectsInJavaFiles.put(openable, l);
                                }
                                JavaElement aspectEl = null;
                                for (Iterator iter = l.iterator(); iter.hasNext();) {
                                    AspectElement element = (AspectElement) iter.next();
                                    if (element.getElementName().equals(aspectName)) {
                                        aspectEl = element;
                                    }
                                }
                                if (aspectEl == null) {
                                    if (openable instanceof ClassFile) {
                                        ClassFile cOpenable = (ClassFile) openable;
                                        aspectEl = new BinaryAspectElement((JavaElement) cOpenable, aspectName);
                                    } else {
                                        aspectEl = new AspectElement((JavaElement) openable, aspectName);
                                    }
                                    l.add(aspectEl);
                                }
                                int afterAspectIndex = index3 + aspectName.length() + 1;

                                if (identifierIsAspect) {
                                    return aspectEl;
                                } else {
                                    memento.setIndexTo(afterAspectIndex);
                                    return aspectEl.getHandleFromMemento(memento.nextToken(), memento, owner);
                                }
                            }
                        }
                    }
                }
            }
        }
        // XXX can we get here???
        if (isCodeElement) {
            // an injar aspect with no parent
            return new AJInjarElement(codeElementHandle);
        }
        return JavaCore.create(handleIdentifier);
    }

    /**
    * Converts a handle signifying Java class to a handle signifying an
    * aspect element.
    * 
    * This method is necessary because JavaCore does not create
    * AspectElements when it is building structure using the {@link AspectsConvertingParser}
    * 
    * Note that this changes the top level class to being an aspect and keeps 
    * all others the same.  This may not work in all situations (eg- an inner aspect)
    * 
    * @param classHandle
    * @return converts the handle to using {@link AspectElement#JEM_ASPECT_CU} and 
    * {@link AspectElement#JEM_ASPECT_TYPE}
    */
    public static String convertToAspectHandle(String classHandle, IJavaElement elt) {
        String aspectHandle = classHandle.replaceFirst("\\" + Character.toString(JavaElement.JEM_TYPE),
                Character.toString(AspectElement.JEM_ASPECT_TYPE));

        if (CoreUtils.ASPECTJ_SOURCE_ONLY_FILTER.accept(elt.getResource().getName())) {
            aspectHandle = aspectHandle.replace(JavaElement.JEM_COMPILATIONUNIT, AspectElement.JEM_ASPECT_CU);
        }
        return aspectHandle;
    }

    public static String convertToJavaCUHandle(String aspectHandle, IJavaElement elt) {
        String javaHandle = aspectHandle;
        if (elt != null) {
            IResource resource = elt.getResource();
            if (resource != null) {
                if (CoreUtils.ASPECTJ_SOURCE_ONLY_FILTER.accept(resource.getName())) {
                    javaHandle = javaHandle.replaceFirst("\\" + AspectElement.JEM_ASPECT_CU,
                            Character.toString(JavaElement.JEM_COMPILATIONUNIT));
                }
            }
        }
        return javaHandle;
    }

}