A crude sketch of find and replace method duplicates.
1.1 --- a/java.hints/hintsimpl/nbproject/genfiles.properties Mon Jul 01 23:46:49 2013 +0200
1.2 +++ b/java.hints/hintsimpl/nbproject/genfiles.properties Sat Jul 06 15:15:21 2013 +0200
1.3 @@ -1,8 +1,8 @@
1.4 -build.xml.data.CRC32=4bedd36b
1.5 +build.xml.data.CRC32=4ab9923f
1.6 build.xml.script.CRC32=ef577a91
1.7 -build.xml.stylesheet.CRC32=a56c6a5b@2.58
1.8 +build.xml.stylesheet.CRC32=a56c6a5b@2.61
1.9 # This file is used by a NetBeans-based IDE to track changes in generated files such as build-impl.xml.
1.10 # Do not edit this file. You may delete it but then the IDE will never regenerate such files for you.
1.11 -nbproject/build-impl.xml.data.CRC32=4bedd36b
1.12 +nbproject/build-impl.xml.data.CRC32=4ab9923f
1.13 nbproject/build-impl.xml.script.CRC32=9204f652
1.14 -nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.58
1.15 +nbproject/build-impl.xml.stylesheet.CRC32=238281d1@2.61
2.1 --- a/java.hints/hintsimpl/nbproject/project.properties Mon Jul 01 23:46:49 2013 +0200
2.2 +++ b/java.hints/hintsimpl/nbproject/project.properties Sat Jul 06 15:15:21 2013 +0200
2.3 @@ -2,3 +2,4 @@
2.4 javac.compilerargs=-Xlint -Xlint:-serial
2.5 requires.nb.javac=true
2.6 spec.version.base=1.0
2.7 +test.runner=junit
3.1 --- a/java.hints/hintsimpl/nbproject/project.xml Mon Jul 01 23:46:49 2013 +0200
3.2 +++ b/java.hints/hintsimpl/nbproject/project.xml Sat Jul 06 15:15:21 2013 +0200
3.3 @@ -16,6 +16,15 @@
3.4 </run-dependency>
3.5 </dependency>
3.6 <dependency>
3.7 + <code-name-base>org.netbeans.api.java.classpath</code-name-base>
3.8 + <build-prerequisite/>
3.9 + <compile-dependency/>
3.10 + <run-dependency>
3.11 + <release-version>1</release-version>
3.12 + <specification-version>1.39</specification-version>
3.13 + </run-dependency>
3.14 + </dependency>
3.15 + <dependency>
3.16 <code-name-base>org.netbeans.libs.javacapi</code-name-base>
3.17 <build-prerequisite/>
3.18 <compile-dependency/>
3.19 @@ -41,6 +50,41 @@
3.20 </run-dependency>
3.21 </dependency>
3.22 <dependency>
3.23 + <code-name-base>org.netbeans.modules.java.sourceui</code-name-base>
3.24 + <build-prerequisite/>
3.25 + <compile-dependency/>
3.26 + <run-dependency>
3.27 + <release-version>1</release-version>
3.28 + <specification-version>1.33.0.1.25</specification-version>
3.29 + </run-dependency>
3.30 + </dependency>
3.31 + <dependency>
3.32 + <code-name-base>org.netbeans.modules.queries</code-name-base>
3.33 + <build-prerequisite/>
3.34 + <compile-dependency/>
3.35 + <run-dependency>
3.36 + <release-version>1</release-version>
3.37 + <specification-version>1.36</specification-version>
3.38 + </run-dependency>
3.39 + </dependency>
3.40 + <dependency>
3.41 + <code-name-base>org.netbeans.modules.refactoring.api</code-name-base>
3.42 + <build-prerequisite/>
3.43 + <compile-dependency/>
3.44 + <run-dependency>
3.45 + <specification-version>1.37.0.1</specification-version>
3.46 + </run-dependency>
3.47 + </dependency>
3.48 + <dependency>
3.49 + <code-name-base>org.netbeans.modules.refactoring.java</code-name-base>
3.50 + <build-prerequisite/>
3.51 + <compile-dependency/>
3.52 + <run-dependency>
3.53 + <release-version>1</release-version>
3.54 + <implementation-version/>
3.55 + </run-dependency>
3.56 + </dependency>
3.57 + <dependency>
3.58 <code-name-base>org.netbeans.spi.editor.hints</code-name-base>
3.59 <build-prerequisite/>
3.60 <compile-dependency/>
3.61 @@ -58,6 +102,46 @@
3.62 </run-dependency>
3.63 </dependency>
3.64 <dependency>
3.65 + <code-name-base>org.openide.awt</code-name-base>
3.66 + <build-prerequisite/>
3.67 + <compile-dependency/>
3.68 + <run-dependency>
3.69 + <specification-version>7.59</specification-version>
3.70 + </run-dependency>
3.71 + </dependency>
3.72 + <dependency>
3.73 + <code-name-base>org.openide.filesystems</code-name-base>
3.74 + <build-prerequisite/>
3.75 + <compile-dependency/>
3.76 + <run-dependency>
3.77 + <specification-version>8.8</specification-version>
3.78 + </run-dependency>
3.79 + </dependency>
3.80 + <dependency>
3.81 + <code-name-base>org.openide.loaders</code-name-base>
3.82 + <build-prerequisite/>
3.83 + <compile-dependency/>
3.84 + <run-dependency>
3.85 + <specification-version>7.50</specification-version>
3.86 + </run-dependency>
3.87 + </dependency>
3.88 + <dependency>
3.89 + <code-name-base>org.openide.nodes</code-name-base>
3.90 + <build-prerequisite/>
3.91 + <compile-dependency/>
3.92 + <run-dependency>
3.93 + <specification-version>7.36</specification-version>
3.94 + </run-dependency>
3.95 + </dependency>
3.96 + <dependency>
3.97 + <code-name-base>org.openide.text</code-name-base>
3.98 + <build-prerequisite/>
3.99 + <compile-dependency/>
3.100 + <run-dependency>
3.101 + <specification-version>6.57</specification-version>
3.102 + </run-dependency>
3.103 + </dependency>
3.104 + <dependency>
3.105 <code-name-base>org.openide.util</code-name-base>
3.106 <build-prerequisite/>
3.107 <compile-dependency/>
3.108 @@ -65,19 +149,48 @@
3.109 <specification-version>8.32</specification-version>
3.110 </run-dependency>
3.111 </dependency>
3.112 + <dependency>
3.113 + <code-name-base>org.openide.util.lookup</code-name-base>
3.114 + <build-prerequisite/>
3.115 + <compile-dependency/>
3.116 + <run-dependency>
3.117 + <specification-version>8.22</specification-version>
3.118 + </run-dependency>
3.119 + </dependency>
3.120 + <dependency>
3.121 + <code-name-base>org.openide.windows</code-name-base>
3.122 + <build-prerequisite/>
3.123 + <compile-dependency/>
3.124 + <run-dependency>
3.125 + <specification-version>6.64</specification-version>
3.126 + </run-dependency>
3.127 + </dependency>
3.128 </module-dependencies>
3.129 <test-dependencies>
3.130 <test-type>
3.131 <name>unit</name>
3.132 <test-dependency>
3.133 + <code-name-base>org.netbeans.libs.junit4</code-name-base>
3.134 + <compile-dependency/>
3.135 + </test-dependency>
3.136 + <test-dependency>
3.137 <code-name-base>org.netbeans.libs.testng</code-name-base>
3.138 <compile-dependency/>
3.139 </test-dependency>
3.140 <test-dependency>
3.141 + <code-name-base>org.netbeans.modules.jackpot30.test.borrowed</code-name-base>
3.142 + <compile-dependency/>
3.143 + </test-dependency>
3.144 + <test-dependency>
3.145 <code-name-base>org.netbeans.modules.java.hints.test</code-name-base>
3.146 <recursive/>
3.147 <compile-dependency/>
3.148 </test-dependency>
3.149 + <test-dependency>
3.150 + <code-name-base>org.netbeans.spi.java.hints</code-name-base>
3.151 + <compile-dependency/>
3.152 + <test/>
3.153 + </test-dependency>
3.154 </test-type>
3.155 </test-dependencies>
3.156 <public-packages/>
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
4.2 +++ b/java.hints/hintsimpl/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/DuplicateMethodRefactoring.java Sat Jul 06 15:15:21 2013 +0200
4.3 @@ -0,0 +1,58 @@
4.4 +/*
4.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
4.6 + *
4.7 + * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
4.8 + *
4.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
4.10 + * Other names may be trademarks of their respective owners.
4.11 + *
4.12 + * The contents of this file are subject to the terms of either the GNU
4.13 + * General Public License Version 2 only ("GPL") or the Common
4.14 + * Development and Distribution License("CDDL") (collectively, the
4.15 + * "License"). You may not use this file except in compliance with the
4.16 + * License. You can obtain a copy of the License at
4.17 + * http://www.netbeans.org/cddl-gplv2.html
4.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
4.19 + * specific language governing permissions and limitations under the
4.20 + * License. When distributing the software, include this License Header
4.21 + * Notice in each file and include the License file at
4.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
4.23 + * particular file as subject to the "Classpath" exception as provided
4.24 + * by Oracle in the GPL Version 2 section of the License file that
4.25 + * accompanied this code. If applicable, add the following below the
4.26 + * License Header, with the fields enclosed by brackets [] replaced by
4.27 + * your own identifying information:
4.28 + * "Portions Copyrighted [year] [name of copyright owner]"
4.29 + *
4.30 + * If you wish your version of this file to be governed by only the CDDL
4.31 + * or only the GPL Version 2, indicate your decision by adding
4.32 + * "[Contributor] elects to include this software in this distribution
4.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
4.34 + * single choice of license, a recipient has the option to distribute
4.35 + * your version of this file under either the CDDL, the GPL Version 2 or
4.36 + * to extend the choice of license to its licensees as provided above.
4.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
4.38 + * Version 2 license, then the option applies only if the new code is
4.39 + * made subject to such option by the copyright holder.
4.40 + *
4.41 + * Contributor(s):
4.42 + *
4.43 + * Portions Copyrighted 2013 Sun Microsystems, Inc.
4.44 + */
4.45 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
4.46 +
4.47 +import org.netbeans.api.java.source.TreePathHandle;
4.48 +import org.netbeans.modules.refactoring.api.AbstractRefactoring;
4.49 +import org.openide.util.lookup.Lookups;
4.50 +
4.51 +/**
4.52 + *
4.53 + * @author lahvac
4.54 + */
4.55 +public class DuplicateMethodRefactoring extends AbstractRefactoring {
4.56 +
4.57 + public DuplicateMethodRefactoring(TreePathHandle source) {
4.58 + super(Lookups.singleton(source));
4.59 + }
4.60 +
4.61 +}
5.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
5.2 +++ b/java.hints/hintsimpl/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/DuplicateMethodRefactoringAction.java Sat Jul 06 15:15:21 2013 +0200
5.3 @@ -0,0 +1,84 @@
5.4 +/*
5.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
5.6 + *
5.7 + * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
5.8 + *
5.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
5.10 + * Other names may be trademarks of their respective owners.
5.11 + *
5.12 + * The contents of this file are subject to the terms of either the GNU
5.13 + * General Public License Version 2 only ("GPL") or the Common
5.14 + * Development and Distribution License("CDDL") (collectively, the
5.15 + * "License"). You may not use this file except in compliance with the
5.16 + * License. You can obtain a copy of the License at
5.17 + * http://www.netbeans.org/cddl-gplv2.html
5.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
5.19 + * specific language governing permissions and limitations under the
5.20 + * License. When distributing the software, include this License Header
5.21 + * Notice in each file and include the License file at
5.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
5.23 + * particular file as subject to the "Classpath" exception as provided
5.24 + * by Oracle in the GPL Version 2 section of the License file that
5.25 + * accompanied this code. If applicable, add the following below the
5.26 + * License Header, with the fields enclosed by brackets [] replaced by
5.27 + * your own identifying information:
5.28 + * "Portions Copyrighted [year] [name of copyright owner]"
5.29 + *
5.30 + * If you wish your version of this file to be governed by only the CDDL
5.31 + * or only the GPL Version 2, indicate your decision by adding
5.32 + * "[Contributor] elects to include this software in this distribution
5.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
5.34 + * single choice of license, a recipient has the option to distribute
5.35 + * your version of this file under either the CDDL, the GPL Version 2 or
5.36 + * to extend the choice of license to its licensees as provided above.
5.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
5.38 + * Version 2 license, then the option applies only if the new code is
5.39 + * made subject to such option by the copyright holder.
5.40 + *
5.41 + * Contributor(s):
5.42 + *
5.43 + * Portions Copyrighted 2013 Sun Microsystems, Inc.
5.44 + */
5.45 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
5.46 +
5.47 +import com.sun.source.tree.Tree.Kind;
5.48 +import java.awt.event.ActionEvent;
5.49 +import java.awt.event.ActionListener;
5.50 +import org.netbeans.api.fileinfo.NonRecursiveFolder;
5.51 +import org.netbeans.api.java.source.CompilationInfo;
5.52 +import org.netbeans.api.java.source.TreePathHandle;
5.53 +import org.netbeans.api.java.source.ui.ScanDialog;
5.54 +import org.netbeans.modules.refactoring.java.ui.ContextAnalyzer;
5.55 +import org.netbeans.modules.refactoring.java.ui.JavaRefactoringUIFactory;
5.56 +import org.netbeans.modules.refactoring.spi.ui.RefactoringUI;
5.57 +import org.openide.awt.ActionID;
5.58 +import org.openide.awt.ActionReference;
5.59 +import org.openide.awt.ActionRegistration;
5.60 +import org.openide.filesystems.FileObject;
5.61 +import org.openide.util.NbBundle.Messages;
5.62 +import org.openide.util.Utilities;
5.63 +
5.64 +@ActionID(
5.65 + category = "Refactoring",
5.66 + id = "org.netbeans.modules.jackpot30.hintsimpl.duplicates.DuplicateMethodRefactoringAction")
5.67 +@ActionRegistration(
5.68 + displayName = "#CTL_DuplicateMethodRefactoringAction")
5.69 +@ActionReference(path = "Menu/Refactoring", position = 1120)
5.70 +@Messages("CTL_DuplicateMethodRefactoringAction=Find and Replace Duplicates...")
5.71 +public final class DuplicateMethodRefactoringAction implements ActionListener {
5.72 +
5.73 + @Override
5.74 + public void actionPerformed(ActionEvent e) {
5.75 + Runnable task = ContextAnalyzer.createTask(Utilities.actionsGlobalContext()/*!!!*/, new JavaRefactoringUIFactory() {
5.76 + @Override public RefactoringUI create(CompilationInfo info, TreePathHandle[] handles, FileObject[] files, NonRecursiveFolder[] packages) {
5.77 + //todo: more precise verification of refactoring feasibility:
5.78 + return handles.length == 1 && handles[0].getKind() == Kind.METHOD ? new DuplicateMethodRefactoringUI(handles[0]) : null;
5.79 + }
5.80 + });
5.81 + ScanDialog.runWhenScanFinished(task, "Find&Replace Duplicates");
5.82 + }
5.83 +
5.84 + public boolean isEnabled() {
5.85 + return ContextAnalyzer.canRefactorSingle(Utilities.actionsGlobalContext()/*!!!*/, true, true);
5.86 + }
5.87 +}
6.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
6.2 +++ b/java.hints/hintsimpl/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/DuplicateMethodRefactoringPlugin.java Sat Jul 06 15:15:21 2013 +0200
6.3 @@ -0,0 +1,183 @@
6.4 +/*
6.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
6.6 + *
6.7 + * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
6.8 + *
6.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
6.10 + * Other names may be trademarks of their respective owners.
6.11 + *
6.12 + * The contents of this file are subject to the terms of either the GNU
6.13 + * General Public License Version 2 only ("GPL") or the Common
6.14 + * Development and Distribution License("CDDL") (collectively, the
6.15 + * "License"). You may not use this file except in compliance with the
6.16 + * License. You can obtain a copy of the License at
6.17 + * http://www.netbeans.org/cddl-gplv2.html
6.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
6.19 + * specific language governing permissions and limitations under the
6.20 + * License. When distributing the software, include this License Header
6.21 + * Notice in each file and include the License file at
6.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
6.23 + * particular file as subject to the "Classpath" exception as provided
6.24 + * by Oracle in the GPL Version 2 section of the License file that
6.25 + * accompanied this code. If applicable, add the following below the
6.26 + * License Header, with the fields enclosed by brackets [] replaced by
6.27 + * your own identifying information:
6.28 + * "Portions Copyrighted [year] [name of copyright owner]"
6.29 + *
6.30 + * If you wish your version of this file to be governed by only the CDDL
6.31 + * or only the GPL Version 2, indicate your decision by adding
6.32 + * "[Contributor] elects to include this software in this distribution
6.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
6.34 + * single choice of license, a recipient has the option to distribute
6.35 + * your version of this file under either the CDDL, the GPL Version 2 or
6.36 + * to extend the choice of license to its licensees as provided above.
6.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
6.38 + * Version 2 license, then the option applies only if the new code is
6.39 + * made subject to such option by the copyright holder.
6.40 + *
6.41 + * Contributor(s):
6.42 + *
6.43 + * Portions Copyrighted 2013 Sun Microsystems, Inc.
6.44 + */
6.45 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
6.46 +
6.47 +import com.sun.source.tree.BlockTree;
6.48 +import com.sun.source.tree.ExpressionTree;
6.49 +import com.sun.source.tree.MethodInvocationTree;
6.50 +import com.sun.source.tree.MethodTree;
6.51 +import com.sun.source.tree.StatementTree;
6.52 +import com.sun.source.util.TreePath;
6.53 +import java.net.URL;
6.54 +import java.util.ArrayList;
6.55 +import java.util.Collection;
6.56 +import java.util.Collections;
6.57 +import java.util.Enumeration;
6.58 +import java.util.HashSet;
6.59 +import java.util.List;
6.60 +import java.util.Set;
6.61 +import javax.lang.model.element.Element;
6.62 +import javax.lang.model.element.ExecutableElement;
6.63 +import javax.lang.model.element.VariableElement;
6.64 +import org.netbeans.api.java.source.CancellableTask;
6.65 +import org.netbeans.api.java.source.ClasspathInfo;
6.66 +import org.netbeans.api.java.source.ClasspathInfo.PathKind;
6.67 +import org.netbeans.api.java.source.JavaSource;
6.68 +import org.netbeans.api.java.source.SourceUtils;
6.69 +import org.netbeans.api.java.source.TreeMaker;
6.70 +import org.netbeans.api.java.source.TreePathHandle;
6.71 +import org.netbeans.api.java.source.WorkingCopy;
6.72 +import org.netbeans.api.java.source.matching.Matcher;
6.73 +import org.netbeans.api.java.source.matching.Occurrence;
6.74 +import org.netbeans.api.java.source.matching.Pattern;
6.75 +import org.netbeans.modules.refactoring.api.Problem;
6.76 +import org.netbeans.modules.refactoring.java.spi.JavaRefactoringPlugin;
6.77 +import org.netbeans.modules.refactoring.spi.RefactoringElementsBag;
6.78 +import org.openide.filesystems.FileObject;
6.79 +import org.openide.filesystems.FileUtil;
6.80 +import org.openide.filesystems.URLMapper;
6.81 +
6.82 +/**
6.83 + *
6.84 + * @author lahvac
6.85 + */
6.86 +public class DuplicateMethodRefactoringPlugin extends JavaRefactoringPlugin {
6.87 + private final DuplicateMethodRefactoring refactoring;
6.88 +
6.89 + DuplicateMethodRefactoringPlugin(DuplicateMethodRefactoring refactoring) {
6.90 + this.refactoring = refactoring;
6.91 + }
6.92 +
6.93 + @Override
6.94 + public Problem preCheck() {
6.95 + return null;
6.96 + }
6.97 +
6.98 + @Override
6.99 + public Problem checkParameters() {
6.100 + return null;
6.101 + }
6.102 +
6.103 + @Override
6.104 + public Problem fastCheckParameters() {
6.105 + return null;
6.106 + }
6.107 +
6.108 + @Override
6.109 + public void cancelRequest() {
6.110 + }
6.111 +
6.112 + @Override
6.113 + public Problem prepare(RefactoringElementsBag refactoringElements) {
6.114 + final TreePathHandle source = refactoring.getRefactoringSource().lookup(TreePathHandle.class);
6.115 + Set<URL> dependent = new HashSet<>();
6.116 +
6.117 + for (FileObject root : ClasspathInfo.create(source.getFileObject()).getClassPath(PathKind.SOURCE).getRoots()) {
6.118 + dependent.add(root.toURL());
6.119 + dependent.addAll(SourceUtils.getDependentRoots(root.toURL()));
6.120 + }
6.121 +
6.122 + Set<FileObject> files = new HashSet<>();
6.123 +
6.124 + for (URL root : dependent) {
6.125 + FileObject rootFO = URLMapper.findFileObject(root);
6.126 +
6.127 + if (rootFO == null) continue;
6.128 +
6.129 + for (Enumeration<? extends FileObject> en = rootFO.getChildren(true); en.hasMoreElements(); ){
6.130 + FileObject file = en.nextElement();
6.131 +
6.132 + if (file.isData() && "text/x-java".equals(FileUtil.getMIMEType(file, "text/x-java"))) {
6.133 + files.add(file);
6.134 + }
6.135 + }
6.136 + }
6.137 +
6.138 + return createAndAddElements(files, new CancellableTask<WorkingCopy>() {
6.139 + @Override public void cancel() {
6.140 + //TODO - is used? if yes, implement.
6.141 + }
6.142 + @Override public void run(WorkingCopy parameter) throws Exception {
6.143 + if (parameter.toPhase(org.netbeans.api.java.source.JavaSource.Phase.RESOLVED).compareTo(org.netbeans.api.java.source.JavaSource.Phase.RESOLVED) < 0) {
6.144 + return ;
6.145 + }
6.146 +
6.147 + Element methodElement = source.getElementHandle().resolve(parameter);
6.148 + TreePath method = parameter.getTrees().getPath(methodElement);
6.149 +
6.150 + if (method == null) {
6.151 + //nothing to do
6.152 + //TODO: create a problem
6.153 + return ;
6.154 + }
6.155 +
6.156 + BlockTree content = ((MethodTree) method.getLeaf()).getBody();
6.157 + TreePath bodyPath = new TreePath(method, content);
6.158 + List<TreePath> statements = new ArrayList<>();
6.159 +
6.160 + for (StatementTree st : content.getStatements()) {
6.161 + statements.add(new TreePath(bodyPath, st));
6.162 + }
6.163 +
6.164 + List<? extends VariableElement> formalParameters = ((ExecutableElement) methodElement).getParameters();
6.165 + Pattern pattern = Pattern.createPatternWithRemappableVariables(statements, formalParameters, true);
6.166 + Collection<? extends Occurrence> found = Matcher.create(parameter).setCancel(cancelRequested).setSearchRoot(new TreePath(parameter.getCompilationUnit())).match(pattern);
6.167 + TreeMaker make = parameter.getTreeMaker();
6.168 +
6.169 + for (Occurrence occ : found) {
6.170 + List<ExpressionTree> newParams = new ArrayList<>();
6.171 + for (VariableElement p : formalParameters) {
6.172 + newParams.add((ExpressionTree) occ.getVariablesRemapToTrees().get(p).getLeaf());
6.173 + }
6.174 + MethodInvocationTree newCall = make.MethodInvocation(Collections.<ExpressionTree>emptyList(), make.QualIdent(methodElement), newParams);
6.175 + parameter.rewrite(occ.getOccurrenceRoot().getLeaf(), make.ExpressionStatement(newCall));
6.176 + }
6.177 + }
6.178 + }, refactoringElements, refactoring);
6.179 + }
6.180 +
6.181 + @Override
6.182 + protected JavaSource getJavaSource(Phase p) {
6.183 + return null;
6.184 + }
6.185 +
6.186 +}
7.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
7.2 +++ b/java.hints/hintsimpl/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/DuplicateMethodRefactoringUI.java Sat Jul 06 15:15:21 2013 +0200
7.3 @@ -0,0 +1,108 @@
7.4 +/*
7.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
7.6 + *
7.7 + * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
7.8 + *
7.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
7.10 + * Other names may be trademarks of their respective owners.
7.11 + *
7.12 + * The contents of this file are subject to the terms of either the GNU
7.13 + * General Public License Version 2 only ("GPL") or the Common
7.14 + * Development and Distribution License("CDDL") (collectively, the
7.15 + * "License"). You may not use this file except in compliance with the
7.16 + * License. You can obtain a copy of the License at
7.17 + * http://www.netbeans.org/cddl-gplv2.html
7.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
7.19 + * specific language governing permissions and limitations under the
7.20 + * License. When distributing the software, include this License Header
7.21 + * Notice in each file and include the License file at
7.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
7.23 + * particular file as subject to the "Classpath" exception as provided
7.24 + * by Oracle in the GPL Version 2 section of the License file that
7.25 + * accompanied this code. If applicable, add the following below the
7.26 + * License Header, with the fields enclosed by brackets [] replaced by
7.27 + * your own identifying information:
7.28 + * "Portions Copyrighted [year] [name of copyright owner]"
7.29 + *
7.30 + * If you wish your version of this file to be governed by only the CDDL
7.31 + * or only the GPL Version 2, indicate your decision by adding
7.32 + * "[Contributor] elects to include this software in this distribution
7.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
7.34 + * single choice of license, a recipient has the option to distribute
7.35 + * your version of this file under either the CDDL, the GPL Version 2 or
7.36 + * to extend the choice of license to its licensees as provided above.
7.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
7.38 + * Version 2 license, then the option applies only if the new code is
7.39 + * made subject to such option by the copyright holder.
7.40 + *
7.41 + * Contributor(s):
7.42 + *
7.43 + * Portions Copyrighted 2013 Sun Microsystems, Inc.
7.44 + */
7.45 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
7.46 +
7.47 +import javax.swing.event.ChangeListener;
7.48 +import org.netbeans.api.java.source.TreePathHandle;
7.49 +import org.netbeans.modules.refactoring.api.AbstractRefactoring;
7.50 +import org.netbeans.modules.refactoring.api.Problem;
7.51 +import org.netbeans.modules.refactoring.spi.ui.CustomRefactoringPanel;
7.52 +import org.netbeans.modules.refactoring.spi.ui.RefactoringUI;
7.53 +import org.openide.util.HelpCtx;
7.54 +
7.55 +/**
7.56 + *
7.57 + * @author lahvac
7.58 + */
7.59 +public class DuplicateMethodRefactoringUI implements RefactoringUI {
7.60 + private final TreePathHandle treePathHandle;
7.61 +
7.62 + DuplicateMethodRefactoringUI(TreePathHandle treePathHandle) {
7.63 + this.treePathHandle = treePathHandle;
7.64 + }
7.65 +
7.66 + @Override
7.67 + public String getName() {
7.68 + return "Duplicate Method Refactoring";
7.69 + }
7.70 +
7.71 + @Override
7.72 + public String getDescription() {
7.73 + return "Duplicate Method Refactoring";
7.74 + }
7.75 +
7.76 + @Override
7.77 + public boolean isQuery() {
7.78 + return false;
7.79 + }
7.80 +
7.81 + @Override
7.82 + public CustomRefactoringPanel getPanel(ChangeListener parent) {
7.83 + return null;
7.84 + }
7.85 +
7.86 + @Override
7.87 + public Problem setParameters() {
7.88 + return null;
7.89 + }
7.90 +
7.91 + @Override
7.92 + public Problem checkParameters() {
7.93 + return null;
7.94 + }
7.95 +
7.96 + @Override
7.97 + public boolean hasParameters() {
7.98 + return false;
7.99 + }
7.100 +
7.101 + @Override
7.102 + public AbstractRefactoring getRefactoring() {
7.103 + return new DuplicateMethodRefactoring(treePathHandle);
7.104 + }
7.105 +
7.106 + @Override
7.107 + public HelpCtx getHelpCtx() {
7.108 + return HelpCtx.DEFAULT_HELP;
7.109 + }
7.110 +
7.111 +}
8.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
8.2 +++ b/java.hints/hintsimpl/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/RefactoringPluginFactoryImpl.java Sat Jul 06 15:15:21 2013 +0200
8.3 @@ -0,0 +1,62 @@
8.4 +/*
8.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
8.6 + *
8.7 + * Copyright 2008-2010 Sun Microsystems, Inc. All rights reserved.
8.8 + *
8.9 + * The contents of this file are subject to the terms of either the GNU
8.10 + * General Public License Version 2 only ("GPL") or the Common
8.11 + * Development and Distribution License("CDDL") (collectively, the
8.12 + * "License"). You may not use this file except in compliance with the
8.13 + * License. You can obtain a copy of the License at
8.14 + * http://www.netbeans.org/cddl-gplv2.html
8.15 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
8.16 + * specific language governing permissions and limitations under the
8.17 + * License. When distributing the software, include this License Header
8.18 + * Notice in each file and include the License file at
8.19 + * nbbuild/licenses/CDDL-GPL-2-CP. Sun designates this
8.20 + * particular file as subject to the "Classpath" exception as provided
8.21 + * by Sun in the GPL Version 2 section of the License file that
8.22 + * accompanied this code. If applicable, add the following below the
8.23 + * License Header, with the fields enclosed by brackets [] replaced by
8.24 + * your own identifying information:
8.25 + * "Portions Copyrighted [year] [name of copyright owner]"
8.26 + *
8.27 + * If you wish your version of this file to be governed by only the CDDL
8.28 + * or only the GPL Version 2, indicate your decision by adding
8.29 + * "[Contributor] elects to include this software in this distribution
8.30 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
8.31 + * single choice of license, a recipient has the option to distribute
8.32 + * your version of this file under either the CDDL, the GPL Version 2 or
8.33 + * to extend the choice of license to its licensees as provided above.
8.34 + * However, if you add GPL Version 2 code and therefore, elected the GPL
8.35 + * Version 2 license, then the option applies only if the new code is
8.36 + * made subject to such option by the copyright holder.
8.37 + *
8.38 + * Contributor(s):
8.39 + *
8.40 + * Portions Copyrighted 2008-2010 Sun Microsystems, Inc.
8.41 + */
8.42 +
8.43 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
8.44 +
8.45 +import org.netbeans.modules.refactoring.api.AbstractRefactoring;
8.46 +import org.netbeans.modules.refactoring.spi.RefactoringPlugin;
8.47 +import org.netbeans.modules.refactoring.spi.RefactoringPluginFactory;
8.48 +import org.openide.util.lookup.ServiceProvider;
8.49 +
8.50 +/**
8.51 + *
8.52 + * @author Jan Lahoda
8.53 + */
8.54 +@ServiceProvider(service=RefactoringPluginFactory.class)
8.55 +public class RefactoringPluginFactoryImpl implements RefactoringPluginFactory {
8.56 +
8.57 + public RefactoringPlugin createInstance(AbstractRefactoring refactoring) {
8.58 + if (refactoring instanceof DuplicateMethodRefactoring) {
8.59 + return new DuplicateMethodRefactoringPlugin((DuplicateMethodRefactoring) refactoring);
8.60 + }
8.61 +
8.62 + return null;
8.63 + }
8.64 +
8.65 +}
9.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
9.2 +++ b/java.hints/hintsimpl/test/unit/src/org/netbeans/modules/jackpot30/hintsimpl/borrowed/RefactoringTestBase.java Sat Jul 06 15:15:21 2013 +0200
9.3 @@ -0,0 +1,387 @@
9.4 +/*
9.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
9.6 + *
9.7 + * Copyright 2009-2010 Sun Microsystems, Inc. All rights reserved.
9.8 + *
9.9 + * The contents of this file are subject to the terms of either the GNU
9.10 + * General Public License Version 2 only ("GPL") or the Common
9.11 + * Development and Distribution License("CDDL") (collectively, the
9.12 + * "License"). You may not use this file except in compliance with the
9.13 + * License. You can obtain a copy of the License at
9.14 + * http://www.netbeans.org/cddl-gplv2.html
9.15 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
9.16 + * specific language governing permissions and limitations under the
9.17 + * License. When distributing the software, include this License Header
9.18 + * Notice in each file and include the License file at
9.19 + * nbbuild/licenses/CDDL-GPL-2-CP. Sun designates this
9.20 + * particular file as subject to the "Classpath" exception as provided
9.21 + * by Sun in the GPL Version 2 section of the License file that
9.22 + * accompanied this code. If applicable, add the following below the
9.23 + * License Header, with the fields enclosed by brackets [] replaced by
9.24 + * your own identifying information:
9.25 + * "Portions Copyrighted [year] [name of copyright owner]"
9.26 + *
9.27 + * If you wish your version of this file to be governed by only the CDDL
9.28 + * or only the GPL Version 2, indicate your decision by adding
9.29 + * "[Contributor] elects to include this software in this distribution
9.30 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
9.31 + * single choice of license, a recipient has the option to distribute
9.32 + * your version of this file under either the CDDL, the GPL Version 2 or
9.33 + * to extend the choice of license to its licensees as provided above.
9.34 + * However, if you add GPL Version 2 code and therefore, elected the GPL
9.35 + * Version 2 license, then the option applies only if the new code is
9.36 + * made subject to such option by the copyright holder.
9.37 + *
9.38 + * Contributor(s):
9.39 + *
9.40 + * Portions Copyrighted 2009-2010 Sun Microsystems, Inc.
9.41 + */
9.42 +package org.netbeans.modules.jackpot30.hintsimpl.borrowed;
9.43 +
9.44 +import java.io.EOFException;
9.45 +import java.io.FileInputStream;
9.46 +import java.io.IOException;
9.47 +import java.nio.charset.Charset;
9.48 +import java.util.Arrays;
9.49 +import java.util.Collections;
9.50 +import java.util.HashMap;
9.51 +import java.util.HashSet;
9.52 +import java.util.Iterator;
9.53 +import java.util.LinkedList;
9.54 +import java.util.List;
9.55 +import java.util.Map;
9.56 +import java.util.logging.Level;
9.57 +import java.util.logging.Logger;
9.58 +import javax.swing.event.ChangeListener;
9.59 +import org.netbeans.api.editor.mimelookup.MimePath;
9.60 +import org.netbeans.api.java.classpath.ClassPath;
9.61 +import org.netbeans.api.java.classpath.GlobalPathRegistry;
9.62 +import org.netbeans.api.java.source.SourceUtilsTestUtil;
9.63 +import org.netbeans.api.java.source.TestUtilities;
9.64 +import org.netbeans.api.java.source.TreeUtilities;
9.65 +import org.netbeans.api.project.Project;
9.66 +import org.netbeans.api.project.ProjectManager;
9.67 +import org.netbeans.api.project.SourceGroup;
9.68 +import org.netbeans.api.project.Sources;
9.69 +import org.netbeans.core.startup.Main;
9.70 +import org.netbeans.junit.NbTestCase;
9.71 +import org.netbeans.modules.java.source.indexing.JavaCustomIndexer;
9.72 +import org.netbeans.modules.parsing.api.indexing.IndexingManager;
9.73 +import org.netbeans.modules.parsing.impl.indexing.CacheFolder;
9.74 +import org.netbeans.modules.parsing.impl.indexing.MimeTypes;
9.75 +import org.netbeans.modules.parsing.impl.indexing.RepositoryUpdater;
9.76 +import org.netbeans.modules.refactoring.api.Problem;
9.77 +import org.netbeans.spi.editor.mimelookup.MimeDataProvider;
9.78 +import org.netbeans.spi.gototest.TestLocator;
9.79 +import org.netbeans.spi.gototest.TestLocator.FileType;
9.80 +import org.netbeans.spi.gototest.TestLocator.LocationListener;
9.81 +import org.netbeans.spi.gototest.TestLocator.LocationResult;
9.82 +import org.netbeans.spi.java.classpath.ClassPathProvider;
9.83 +import org.netbeans.spi.java.classpath.support.ClassPathSupport;
9.84 +import org.netbeans.spi.project.ProjectFactory;
9.85 +import org.netbeans.spi.project.ProjectState;
9.86 +import org.netbeans.spi.project.support.GenericSources;
9.87 +import org.openide.filesystems.FileObject;
9.88 +import org.openide.filesystems.FileUtil;
9.89 +import org.openide.util.Lookup;
9.90 +import org.openide.util.NbBundle;
9.91 +import org.openide.util.lookup.Lookups;
9.92 +import org.openide.util.lookup.ServiceProvider;
9.93 +
9.94 +public class RefactoringTestBase extends NbTestCase {
9.95 + // Turning off annoying info messages from treeutilities
9.96 + private static final Logger TREEUTILITIESLOGGER = Logger.getLogger(TreeUtilities.class.getName());
9.97 +
9.98 + public RefactoringTestBase(String name) {
9.99 + super(name);
9.100 + }
9.101 +
9.102 + protected static void writeFilesAndWaitForScan(FileObject sourceRoot, File... files) throws Exception {
9.103 + for (FileObject c : sourceRoot.getChildren()) {
9.104 + c.delete();
9.105 + }
9.106 +
9.107 + for (File f : files) {
9.108 + FileObject fo = FileUtil.createData(sourceRoot, f.filename);
9.109 + TestUtilities.copyStringToFile(fo, f.content);
9.110 + }
9.111 +
9.112 + IndexingManager.getDefault().refreshIndexAndWait(sourceRoot.toURL(), null, true);
9.113 + }
9.114 +
9.115 + protected void verifyContent(FileObject sourceRoot, File... files) throws Exception {
9.116 + List<FileObject> todo = new LinkedList<FileObject>();
9.117 +
9.118 + todo.add(sourceRoot);
9.119 +
9.120 + Map<String, String> content = new HashMap<String, String>();
9.121 +
9.122 + FileUtil.refreshFor(FileUtil.toFile(sourceRoot));
9.123 +
9.124 + while (!todo.isEmpty()) {
9.125 + FileObject file = todo.remove(0);
9.126 +
9.127 + if (file.isData()) {
9.128 + content.put(FileUtil.getRelativePath(sourceRoot, file), copyFileToString(FileUtil.toFile(file)));
9.129 + } else {
9.130 + todo.addAll(Arrays.asList(file.getChildren()));
9.131 + }
9.132 + }
9.133 +
9.134 + for (File f : files) {
9.135 + String fileContent = content.remove(f.filename);
9.136 +
9.137 + assertNotNull(f);
9.138 + assertNotNull(f.content);
9.139 + assertNotNull("Cannot find " + f.filename + " in map " + content, fileContent);
9.140 + assertEquals(getName() ,f.content.replaceAll("[ \t\r\n\n]+", " "), fileContent.replaceAll("[ \t\r\n\n]+", " "));
9.141 + }
9.142 +
9.143 + assertTrue(content.toString(), content.isEmpty());
9.144 + }
9.145 +
9.146 + /**
9.147 + * Returns a string which contains the contents of a file.
9.148 + *
9.149 + * @param f the file to be read
9.150 + * @return the contents of the file(s).
9.151 + */
9.152 + private static String copyFileToString(java.io.File f) throws java.io.IOException {
9.153 + int s = (int) f.length();
9.154 + byte[] data = new byte[s];
9.155 + int len = new FileInputStream(f).read(data);
9.156 + if (len != s) {
9.157 + throw new EOFException("truncated file");
9.158 + }
9.159 + return new String(data, Charset.forName("UTF8"));
9.160 + }
9.161 +
9.162 + protected static void addAllProblems(List<Problem> problems, Problem head) {
9.163 + while (head != null) {
9.164 + problems.add(head);
9.165 + head = head.getNext();
9.166 + }
9.167 + }
9.168 +
9.169 + protected static void assertProblems(Iterable<? extends Problem> golden, Iterable<? extends Problem> real) {
9.170 + Iterator<? extends Problem> g = golden.iterator();
9.171 + Iterator<? extends Problem> r = real.iterator();
9.172 +
9.173 + while (g.hasNext() && r.hasNext()) {
9.174 + Problem gp = g.next();
9.175 + Problem rp = r.next();
9.176 +
9.177 + assertEquals(gp.isFatal(), rp.isFatal());
9.178 + assertEquals(gp.getMessage(), rp.getMessage());
9.179 + }
9.180 + boolean goldenHasNext = g.hasNext();
9.181 + boolean realHasNext = r.hasNext();
9.182 +
9.183 + assertFalse(goldenHasNext?"Expected: " + g.next().getMessage():"", goldenHasNext);
9.184 + assertFalse(realHasNext?"Unexpected: " + r.next().getMessage():"", realHasNext);
9.185 + }
9.186 +
9.187 + static {
9.188 + NbBundle.setBranding("test");
9.189 + }
9.190 +
9.191 + protected static final class File {
9.192 + public final String filename;
9.193 + public final String content;
9.194 +
9.195 + public File(String filename, String content) {
9.196 + this.filename = filename;
9.197 + this.content = content;
9.198 + }
9.199 + }
9.200 +
9.201 + protected FileObject src;
9.202 + protected FileObject test;
9.203 + protected Project prj;
9.204 + private ClassPath sourcePath;
9.205 +
9.206 + @Override
9.207 + protected void setUp() throws Exception {
9.208 + System.setProperty("org.netbeans.modules.java.source.usages.SourceAnalyser.fullIndex", "true");
9.209 + TREEUTILITIESLOGGER.setLevel(Level.SEVERE);
9.210 + MimeTypes.setAllMimeTypes(new HashSet<String>());
9.211 + SourceUtilsTestUtil.prepareTest(new String[] {"org/netbeans/modules/openide/loaders/layer.xml",
9.212 + "org/netbeans/modules/java/source/resources/layer.xml",
9.213 + "org/netbeans/modules/java/editor/resources/layer.xml",
9.214 + /*"org/netbeans/modules/refactoring/java/test/resources/layer.xml", */"META-INF/generated-layer.xml"}, new Object[] {
9.215 + new ClassPathProvider() {
9.216 + @Override
9.217 + public ClassPath findClassPath(FileObject file, String type) {
9.218 + if (sourcePath != null && sourcePath.contains(file)){
9.219 + if (ClassPath.BOOT.equals(type)) {
9.220 + return ClassPathSupport.createClassPath(System.getProperty("sun.boot.class.path"));
9.221 + }
9.222 + if (ClassPath.COMPILE.equals(type)) {
9.223 + return ClassPathSupport.createClassPath(new FileObject[0]);
9.224 + }
9.225 + if (ClassPath.SOURCE.equals(type)) {
9.226 + return sourcePath;
9.227 + }
9.228 + }
9.229 +
9.230 + return null;
9.231 + }
9.232 + },
9.233 + new ProjectFactory() {
9.234 + @Override
9.235 + public boolean isProject(FileObject projectDirectory) {
9.236 + return src != null && src.getParent() == projectDirectory;
9.237 + }
9.238 + @Override
9.239 + public Project loadProject(final FileObject projectDirectory, ProjectState state) throws IOException {
9.240 + if (!isProject(projectDirectory)) {
9.241 + return null;
9.242 + }
9.243 + return new Project() {
9.244 + @Override
9.245 + public FileObject getProjectDirectory() {
9.246 + return projectDirectory;
9.247 + }
9.248 + @Override
9.249 + public Lookup getLookup() {
9.250 + final Project p = this;
9.251 + return Lookups.singleton(new Sources() {
9.252 +
9.253 + @Override
9.254 + public SourceGroup[] getSourceGroups(String type) {
9.255 + return new SourceGroup[] {GenericSources.group(p, src.getParent(), "source", "Java Sources", null, null),
9.256 + GenericSources.group(p, test, "testsources", "Test Sources", null, null)};
9.257 + }
9.258 +
9.259 + @Override
9.260 + public void addChangeListener(ChangeListener listener) {
9.261 + }
9.262 +
9.263 + @Override
9.264 + public void removeChangeListener(ChangeListener listener) {
9.265 + }
9.266 + });
9.267 + }
9.268 + };
9.269 + }
9.270 + @Override
9.271 + public void saveProject(Project project) throws IOException, ClassCastException {}
9.272 + },
9.273 + new TestLocator() {
9.274 +
9.275 + @Override
9.276 + public boolean appliesTo(FileObject fo) {
9.277 + return true;
9.278 + }
9.279 +
9.280 + @Override
9.281 + public boolean asynchronous() {
9.282 + return false;
9.283 + }
9.284 +
9.285 + @Override
9.286 + public LocationResult findOpposite(FileObject fo, int caretOffset) {
9.287 + ClassPath srcCp;
9.288 +
9.289 + if ((srcCp = ClassPath.getClassPath(fo, ClassPath.SOURCE)) == null) {
9.290 + return new LocationResult("File not found"); //NOI18N
9.291 + }
9.292 +
9.293 + String baseResName = srcCp.getResourceName(fo, '/', false);
9.294 + String testResName = getTestResName(baseResName, fo.getExt());
9.295 + assert testResName != null;
9.296 + FileObject fileObject = test.getFileObject(testResName);
9.297 + if(fileObject != null) {
9.298 + return new LocationResult(fileObject, -1);
9.299 + }
9.300 +
9.301 + return new LocationResult("File not found"); //NOI18N
9.302 + }
9.303 +
9.304 + @Override
9.305 + public void findOpposite(FileObject fo, int caretOffset, LocationListener callback) {
9.306 + throw new UnsupportedOperationException("This should not be called on synchronous locators.");
9.307 + }
9.308 +
9.309 + @Override
9.310 + public FileType getFileType(FileObject fo) {
9.311 + if(FileUtil.isParentOf(test, fo)) {
9.312 + return FileType.TEST;
9.313 + } else if(FileUtil.isParentOf(src, fo)) {
9.314 + return FileType.TESTED;
9.315 + }
9.316 + return FileType.NEITHER;
9.317 + }
9.318 +
9.319 + private String getTestResName(String baseResName, String ext) {
9.320 + StringBuilder buf
9.321 + = new StringBuilder(baseResName.length() + ext.length() + 10);
9.322 + buf.append(baseResName).append("Test"); //NOI18N
9.323 + if (ext.length() != 0) {
9.324 + buf.append('.').append(ext);
9.325 + }
9.326 + return buf.toString();
9.327 + }
9.328 + }});
9.329 + Main.initializeURLFactory();
9.330 + org.netbeans.api.project.ui.OpenProjects.getDefault().getOpenProjects();
9.331 + prepareTest();
9.332 + org.netbeans.api.project.ui.OpenProjects.getDefault().open(new Project[] {prj = ProjectManager.getDefault().findProject(src.getParent())}, false);
9.333 + MimeTypes.setAllMimeTypes(Collections.singleton("text/x-java"));
9.334 + sourcePath = ClassPathSupport.createClassPath(src, test);
9.335 + GlobalPathRegistry.getDefault().register(ClassPath.SOURCE, new ClassPath[] {sourcePath});
9.336 + RepositoryUpdater.getDefault().start(true);
9.337 + super.setUp();
9.338 + FileUtil.createData(FileUtil.getConfigRoot(), "Templates/Classes/Empty.java");
9.339 + System.setProperty("org.netbeans.modules.parsing.impl.Source.excludedTasks", ".*");
9.340 + }
9.341 +
9.342 + @Override
9.343 + protected void tearDown() throws Exception {
9.344 + super.tearDown();
9.345 + GlobalPathRegistry.getDefault().unregister(ClassPath.SOURCE, new ClassPath[] {sourcePath});
9.346 + org.netbeans.api.project.ui.OpenProjects.getDefault().close(new Project[] {prj});
9.347 + prj = null;
9.348 + }
9.349 +
9.350 + private void prepareTest() throws Exception {
9.351 + FileObject workdir = SourceUtilsTestUtil.makeScratchDir(this);
9.352 +
9.353 + FileObject projectFolder = FileUtil.createFolder(workdir, "testProject");
9.354 + src = FileUtil.createFolder(projectFolder, "src");
9.355 + test = FileUtil.createFolder(projectFolder, "test");
9.356 +
9.357 + FileObject cache = FileUtil.createFolder(workdir, "cache");
9.358 +
9.359 + CacheFolder.setCacheFolder(cache);
9.360 + }
9.361 +
9.362 + @ServiceProvider(service=MimeDataProvider.class)
9.363 + public static final class MimeDataProviderImpl implements MimeDataProvider {
9.364 +
9.365 + private static final Lookup L = Lookups.singleton(new JavaCustomIndexer.Factory());
9.366 +
9.367 + @Override
9.368 + public Lookup getLookup(MimePath mimePath) {
9.369 + if ("text/x-java".equals(mimePath.getPath())) {
9.370 + return L;
9.371 + }
9.372 +
9.373 + return null;
9.374 + }
9.375 +
9.376 + }
9.377 +
9.378 + protected static boolean problemIsFatal(List<Problem> problems) {
9.379 + for (Problem problem : problems) {
9.380 + Problem next = problem;
9.381 + do {
9.382 + if (next.isFatal()) {
9.383 + return true;
9.384 + }
9.385 + next = next.getNext();
9.386 + } while (next != null);
9.387 + }
9.388 + return false;
9.389 + }
9.390 +}
9.391 \ No newline at end of file
10.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
10.2 +++ b/java.hints/hintsimpl/test/unit/src/org/netbeans/modules/jackpot30/hintsimpl/duplicates/DuplicateMethodRefactoringPluginTest.java Sat Jul 06 15:15:21 2013 +0200
10.3 @@ -0,0 +1,165 @@
10.4 +/*
10.5 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
10.6 + *
10.7 + * Copyright 2013 Oracle and/or its affiliates. All rights reserved.
10.8 + *
10.9 + * Oracle and Java are registered trademarks of Oracle and/or its affiliates.
10.10 + * Other names may be trademarks of their respective owners.
10.11 + *
10.12 + * The contents of this file are subject to the terms of either the GNU
10.13 + * General Public License Version 2 only ("GPL") or the Common
10.14 + * Development and Distribution License("CDDL") (collectively, the
10.15 + * "License"). You may not use this file except in compliance with the
10.16 + * License. You can obtain a copy of the License at
10.17 + * http://www.netbeans.org/cddl-gplv2.html
10.18 + * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
10.19 + * specific language governing permissions and limitations under the
10.20 + * License. When distributing the software, include this License Header
10.21 + * Notice in each file and include the License file at
10.22 + * nbbuild/licenses/CDDL-GPL-2-CP. Oracle designates this
10.23 + * particular file as subject to the "Classpath" exception as provided
10.24 + * by Oracle in the GPL Version 2 section of the License file that
10.25 + * accompanied this code. If applicable, add the following below the
10.26 + * License Header, with the fields enclosed by brackets [] replaced by
10.27 + * your own identifying information:
10.28 + * "Portions Copyrighted [year] [name of copyright owner]"
10.29 + *
10.30 + * If you wish your version of this file to be governed by only the CDDL
10.31 + * or only the GPL Version 2, indicate your decision by adding
10.32 + * "[Contributor] elects to include this software in this distribution
10.33 + * under the [CDDL or GPL Version 2] license." If you do not indicate a
10.34 + * single choice of license, a recipient has the option to distribute
10.35 + * your version of this file under either the CDDL, the GPL Version 2 or
10.36 + * to extend the choice of license to its licensees as provided above.
10.37 + * However, if you add GPL Version 2 code and therefore, elected the GPL
10.38 + * Version 2 license, then the option applies only if the new code is
10.39 + * made subject to such option by the copyright holder.
10.40 + *
10.41 + * Contributor(s):
10.42 + *
10.43 + * Portions Copyrighted 2013 Sun Microsystems, Inc.
10.44 + */
10.45 +package org.netbeans.modules.jackpot30.hintsimpl.duplicates;
10.46 +
10.47 +import java.util.Arrays;
10.48 +import java.util.LinkedList;
10.49 +import java.util.List;
10.50 +import javax.lang.model.element.ExecutableElement;
10.51 +import javax.lang.model.util.ElementFilter;
10.52 +import org.netbeans.api.java.source.CompilationController;
10.53 +import org.netbeans.api.java.source.JavaSource;
10.54 +import org.netbeans.api.java.source.Task;
10.55 +import org.netbeans.api.java.source.TreePathHandle;
10.56 +import org.netbeans.modules.jackpot30.hintsimpl.borrowed.RefactoringTestBase;
10.57 +import org.netbeans.modules.refactoring.api.Problem;
10.58 +import org.netbeans.modules.refactoring.api.RefactoringSession;
10.59 +
10.60 +/**
10.61 + *
10.62 + * @author lahvac
10.63 + */
10.64 +public class DuplicateMethodRefactoringPluginTest extends RefactoringTestBase {
10.65 +
10.66 + public DuplicateMethodRefactoringPluginTest(String name) {
10.67 + super(name);
10.68 + }
10.69 +
10.70 + public void testSimple() throws Exception {
10.71 + writeFilesAndWaitForScan(src,
10.72 + new File("test/Test.java",
10.73 + "package test;\n" +
10.74 + "public class Test {\n" +
10.75 + " public static void toCall() {\n" +
10.76 + " System.err.println(1);\n" +
10.77 + " }\n" +
10.78 + " public static void test1() {\n" +
10.79 + " System.err.println(1);\n" +
10.80 + " }\n" +
10.81 + " public static void test2() {\n" +
10.82 + " System.out.println(1);\n" +
10.83 + " }\n" +
10.84 + " public static void test3() {\n" +
10.85 + " System.err.println(2);\n" +
10.86 + " }\n" +
10.87 + "}\n"));
10.88 + performDuplicateMethod("toCall");
10.89 + verifyContent(src,
10.90 + new File("test/Test.java",
10.91 + "package test;\n" +
10.92 + "public class Test {\n" +
10.93 + " public static void toCall() {\n" +
10.94 + " System.err.println(1);\n" +
10.95 + " }\n" +
10.96 + " public static void test1() {\n" +
10.97 + " toCall();\n" +
10.98 + " }\n" +
10.99 + " public static void test2() {\n" +
10.100 + " System.out.println(1);\n" +
10.101 + " }\n" +
10.102 + " public static void test3() {\n" +
10.103 + " System.err.println(2);\n" +
10.104 + " }\n" +
10.105 + "}\n"));
10.106 + }
10.107 +
10.108 + public void testParams() throws Exception {
10.109 + writeFilesAndWaitForScan(src,
10.110 + new File("test/Test.java",
10.111 + "package test;\n" +
10.112 + "public class Test {\n" +
10.113 + " public static void toCall(int i) {\n" +
10.114 + " System.err.println(i);\n" +
10.115 + " }\n" +
10.116 + " public static void test1(int j) {\n" +
10.117 + " System.err.println(1 + j);\n" +
10.118 + " }\n" +
10.119 + " public static void test3() {\n" +
10.120 + " System.err.println(2);\n" +
10.121 + " }\n" +
10.122 + "}\n"));
10.123 + performDuplicateMethod("toCall");
10.124 + verifyContent(src,
10.125 + new File("test/Test.java",
10.126 + "package test;\n" +
10.127 + "public class Test {\n" +
10.128 + " public static void toCall(int i) {\n" +
10.129 + " System.err.println(i);\n" +
10.130 + " }\n" +
10.131 + " public static void test1(int j) {\n" +
10.132 + " toCall(1 + j);\n" +
10.133 + " }\n" +
10.134 + " public static void test3() {\n" +
10.135 + " toCall(2);\n" +
10.136 + " }\n" +
10.137 + "}\n"));
10.138 + }
10.139 +
10.140 + private void performDuplicateMethod(final String methodName, Problem... expectedProblems) throws Exception {
10.141 + final DuplicateMethodRefactoring[] r = new DuplicateMethodRefactoring[1];
10.142 +
10.143 + JavaSource.forFileObject(src.getFileObject("test/Test.java")).runUserActionTask(new Task<CompilationController>() {
10.144 + @Override public void run(CompilationController javac) throws Exception {
10.145 + javac.toPhase(JavaSource.Phase.RESOLVED);
10.146 +
10.147 + for (ExecutableElement method : ElementFilter.methodsIn(javac.getTopLevelElements().get(0).getEnclosedElements())) {
10.148 + if (method.getSimpleName().contentEquals(methodName)) {
10.149 + r[0] = new DuplicateMethodRefactoring(TreePathHandle.create(javac.getTrees().getPath(method), javac));
10.150 + }
10.151 + }
10.152 + }
10.153 + }, true);
10.154 +
10.155 + RefactoringSession rs = RefactoringSession.create("Session");
10.156 + List<Problem> problems = new LinkedList<Problem>();
10.157 +
10.158 + addAllProblems(problems, r[0].preCheck());
10.159 + if (!problemIsFatal(problems)) {
10.160 + addAllProblems(problems, r[0].prepare(rs));
10.161 + }
10.162 + if (!problemIsFatal(problems)) {
10.163 + addAllProblems(problems, rs.doRefactoring(true));
10.164 + }
10.165 +
10.166 + assertProblems(Arrays.asList(expectedProblems), problems);
10.167 + }
10.168 +}