Skip to content

Commit

Permalink
Handle CompletableFutures more consistently across the board
Browse files Browse the repository at this point in the history
Fixes #243
Fixes #240

Signed-off-by: Fred Bricon <[email protected]>
  • Loading branch information
fbricon committed Jun 9, 2017
1 parent 0c5ace6 commit 277ee17
Show file tree
Hide file tree
Showing 19 changed files with 176 additions and 177 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -10,42 +10,42 @@
*******************************************************************************/
package org.eclipse.jdt.ls.core.internal.handlers;

import java.util.concurrent.CompletableFuture;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.IBuffer;
import org.eclipse.jdt.core.IClassFile;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jdt.ls.core.internal.JDTUtils;
import org.eclipse.jdt.ls.core.internal.JavaLanguageServerPlugin;
import org.eclipse.lsp4j.TextDocumentIdentifier;
import org.eclipse.lsp4j.jsonrpc.CompletableFutures;

public class ClassfileContentHandler {

public CompletableFuture<String> contents(TextDocumentIdentifier param) {
return CompletableFutures.computeAsync(cm->{
String source = null;
try {
IClassFile cf = JDTUtils.resolveClassFile(param.getUri());
if (cf != null) {
IBuffer buffer = cf.getBuffer();
if (buffer != null){
cm.checkCanceled();
JavaLanguageServerPlugin.logInfo("ClassFile contents request completed");
source = buffer.getContents();
}
if (source == null) {
source = JDTUtils.disassemble(cf);
private static final String EMPTY_CONTENT = "";

public String contents(TextDocumentIdentifier param, IProgressMonitor monitor) {
String source = null;
try {
IClassFile cf = JDTUtils.resolveClassFile(param.getUri());
if (cf != null) {
IBuffer buffer = cf.getBuffer();
if (buffer != null) {
if (monitor.isCanceled()) {
return EMPTY_CONTENT;
}
source = buffer.getContents();
JavaLanguageServerPlugin.logInfo("ClassFile contents request completed");
}
if (source == null) {
source = JDTUtils.disassemble(cf);
}
} catch (JavaModelException e) {
JavaLanguageServerPlugin.logException("Exception getting java element ", e);
}
if (source == null) {
source = "";//need to return non null value
}
return source;
});
} catch (JavaModelException e) {
JavaLanguageServerPlugin.logException("Exception getting java element ", e);
}
if (source == null) {
source = EMPTY_CONTENT;// need to return non null value
}
return source;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@

import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.ICompilationUnit;
import org.eclipse.jdt.core.IJavaElement;
import org.eclipse.jdt.core.IJavaProject;
Expand Down Expand Up @@ -51,7 +51,7 @@ public CodeLensHandler(PreferenceManager preferenceManager) {
}

@SuppressWarnings("unchecked")
public CodeLens resolve(CodeLens lens){
public CodeLens resolve(CodeLens lens, IProgressMonitor monitor) {
if (lens == null) {
return null;
}
Expand All @@ -67,7 +67,7 @@ public CodeLens resolve(CodeLens lens){
}
Map<String, Object> position = (Map<String, Object>) data.get(1);
IJavaElement element = JDTUtils.findElementAtSelection(unit, ((Double)position.get("line")).intValue(), ((Double)position.get("character")).intValue());
List<Location> locations = findReferences(element);
List<Location> locations = findReferences(element, monitor);
int nReferences = locations.size();
Command command = new Command(nReferences == 1 ? "1 reference" : nReferences + " references",
"java.show.references",
Expand All @@ -79,7 +79,8 @@ public CodeLens resolve(CodeLens lens){
return lens;
}

private List<Location> findReferences(IJavaElement element) throws JavaModelException, CoreException {
private List<Location> findReferences(IJavaElement element, IProgressMonitor monitor)
throws JavaModelException, CoreException {
if (element == null) {
return Collections.emptyList();
}
Expand All @@ -106,12 +107,12 @@ public void acceptSearchMatch(SearchMatch match) throws CoreException {
}

}
}, new NullProgressMonitor());
}, monitor);

return result;
}

public List<CodeLens> getCodeLensSymbols(String uri) {
public List<CodeLens> getCodeLensSymbols(String uri, IProgressMonitor monitor) {
if (!preferenceManager.getPreferences().isReferencesCodeLensEnabled()) {
return Collections.emptyList();
}
Expand All @@ -122,19 +123,26 @@ public List<CodeLens> getCodeLensSymbols(String uri) {
try {
IJavaElement[] elements = unit.getChildren();
ArrayList<CodeLens> lenses = new ArrayList<>(elements.length);
collectChildren(unit, elements, lenses);
collectChildren(unit, elements, lenses, monitor);
if (monitor.isCanceled()) {
lenses.clear();
}
return lenses;
} catch (JavaModelException e) {
JavaLanguageServerPlugin.logException("Problem getting code lenses for" + unit.getElementName(), e);
}
return Collections.emptyList();
}

private void collectChildren(ICompilationUnit unit, IJavaElement[] elements, ArrayList<CodeLens> lenses)
private void collectChildren(ICompilationUnit unit, IJavaElement[] elements, ArrayList<CodeLens> lenses,
IProgressMonitor monitor)
throws JavaModelException {
for (IJavaElement element : elements) {
if (monitor.isCanceled()) {
return;
}
if (element.getElementType() == IJavaElement.TYPE) {
collectChildren(unit, ((IType) element).getChildren(), lenses);
collectChildren(unit, ((IType) element).getChildren(), lenses, monitor);
} else if (element.getElementType() != IJavaElement.METHOD || JDTUtils.isHiddenGeneratedElement(element)) {
continue;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,41 +13,37 @@
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.CompletableFuture;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.CompletionProposal;
import org.eclipse.jdt.core.ICompilationUnit;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jdt.ls.core.internal.CancellableProgressMonitor;
import org.eclipse.jdt.ls.core.internal.JDTUtils;
import org.eclipse.jdt.ls.core.internal.JavaLanguageServerPlugin;
import org.eclipse.jdt.ls.core.internal.contentassist.CompletionProposalRequestor;
import org.eclipse.lsp4j.CompletionItem;
import org.eclipse.lsp4j.CompletionList;
import org.eclipse.lsp4j.TextDocumentPositionParams;
import org.eclipse.lsp4j.jsonrpc.CompletableFutures;
import org.eclipse.lsp4j.jsonrpc.messages.Either;

public class CompletionHandler{

CompletableFuture<Either<List<CompletionItem>, CompletionList>> completion(TextDocumentPositionParams position){
return CompletableFutures.computeAsync(cancelChecker->{
List<CompletionItem> completionItems;
try {
ICompilationUnit unit = JDTUtils.resolveCompilationUnit(position.getTextDocument().getUri());
completionItems = this.computeContentAssist(unit,
position.getPosition().getLine(),
position.getPosition().getCharacter(), new CancellableProgressMonitor(cancelChecker));
} catch (Exception e) {
JavaLanguageServerPlugin.logException("Problem with codeComplete for " + position.getTextDocument().getUri(), e);
completionItems = Collections.emptyList();
}
CompletionList $ = new CompletionList();
$.setItems(completionItems);
JavaLanguageServerPlugin.logInfo("Completion request completed");
return Either.forRight($);
});
Either<List<CompletionItem>, CompletionList> completion(TextDocumentPositionParams position,
IProgressMonitor monitor) {
List<CompletionItem> completionItems;
try {
ICompilationUnit unit = JDTUtils.resolveCompilationUnit(position.getTextDocument().getUri());
completionItems = this.computeContentAssist(unit,
position.getPosition().getLine(),
position.getPosition().getCharacter(), monitor);
} catch (Exception e) {
JavaLanguageServerPlugin.logException("Problem with codeComplete for " + position.getTextDocument().getUri(), e);
completionItems = Collections.emptyList();
}
CompletionList $ = new CompletionList();
$.setItems(completionItems);
JavaLanguageServerPlugin.logInfo("Completion request completed");
return Either.forRight($);
}

private List<CompletionItem> computeContentAssist(ICompilationUnit unit, int line, int column, IProgressMonitor monitor) throws JavaModelException {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
import java.util.Map;
import java.util.concurrent.TimeUnit;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.ICompilationUnit;
import org.eclipse.jdt.core.IField;
import org.eclipse.jdt.core.IMember;
Expand Down Expand Up @@ -61,7 +62,7 @@ public CompletionResolveHandler(PreferenceManager manager) {
public static final String DATA_FIELD_REQUEST_ID = "rid";
public static final String DATA_FIELD_PROPOSAL_ID = "pid";

public CompletionItem resolve(CompletionItem param) {
public CompletionItem resolve(CompletionItem param, IProgressMonitor monitor) {

@SuppressWarnings("unchecked")
Map<String, String> data = (Map<String, String>) param.getData();
Expand Down Expand Up @@ -117,7 +118,7 @@ public CompletionItem resolve(CompletionItem param) {
member = type;
}

if (member!=null && member.exists()) {
if (member != null && member.exists() && !monitor.isCanceled()) {
String javadoc = null;
try {
final IMember curMember = member;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,8 @@
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.CompletableFuture;

import org.eclipse.core.runtime.NullProgressMonitor;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.ITypeRoot;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jdt.core.dom.CompilationUnit;
Expand All @@ -34,19 +33,22 @@
@SuppressWarnings("restriction")
public class DocumentHighlightHandler{

private List<DocumentHighlight> computeOccurrences(ITypeRoot unit, int line, int column) {
private List<DocumentHighlight> computeOccurrences(ITypeRoot unit, int line, int column, IProgressMonitor monitor) {
if (unit != null) {
try {
int offset = JsonRpcHelpers.toOffset(unit.getBuffer(), line, column);
OccurrencesFinder finder = new OccurrencesFinder();
CompilationUnit ast = SharedASTProvider.getInstance().getAST(unit, new NullProgressMonitor());
CompilationUnit ast = SharedASTProvider.getInstance().getAST(unit, monitor);
if (ast != null) {
String error = finder.initialize(ast, offset, 0);
if (error == null){
List<DocumentHighlight> result = new ArrayList<>();
OccurrenceLocation[] occurrences = finder.getOccurrences();
if (occurrences != null) {
for (OccurrenceLocation loc : occurrences) {
if (monitor.isCanceled()) {
return Collections.emptyList();
}
result.add(convertToHighlight(unit, loc));
}
}
Expand Down Expand Up @@ -79,12 +81,10 @@ private DocumentHighlight convertToHighlight(ITypeRoot unit, OccurrenceLocation
return h;
}

CompletableFuture<List<? extends DocumentHighlight>> documentHighlight(TextDocumentPositionParams position){
return CompletableFuture.supplyAsync(()->{
ITypeRoot type = JDTUtils.resolveTypeRoot(position.getTextDocument().getUri());
return computeOccurrences(type, position.getPosition().getLine(),
position.getPosition().getCharacter());
});
List<? extends DocumentHighlight> documentHighlight(TextDocumentPositionParams position, IProgressMonitor monitor) {
ITypeRoot type = JDTUtils.resolveTypeRoot(position.getTextDocument().getUri());
return computeOccurrences(type, position.getPosition().getLine(),
position.getPosition().getCharacter(), monitor);
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,9 @@
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.stream.Stream;

import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.Flags;
import org.eclipse.jdt.core.IJavaElement;
import org.eclipse.jdt.core.IMember;
Expand All @@ -34,23 +34,37 @@

public class DocumentSymbolHandler {

private SymbolInformation[] getOutline(ITypeRoot unit) {
public List<? extends SymbolInformation> documentSymbol(DocumentSymbolParams params,
IProgressMonitor monitor) {
ITypeRoot unit = JDTUtils.resolveTypeRoot(params.getTextDocument().getUri());
if (unit == null) {
return Collections.emptyList();
}
SymbolInformation[] elements = this.getOutline(unit, monitor);
return Arrays.asList(elements);
}

private SymbolInformation[] getOutline(ITypeRoot unit, IProgressMonitor monitor) {
try {
IJavaElement[] elements = unit.getChildren();
ArrayList<SymbolInformation> symbols = new ArrayList<>(elements.length);
collectChildren(unit, elements, symbols);
collectChildren(unit, elements, symbols, monitor);
return symbols.toArray(new SymbolInformation[symbols.size()]);
} catch (JavaModelException e) {
JavaLanguageServerPlugin.logException("Problem getting outline for" + unit.getElementName(), e);
}
return new SymbolInformation[0];
}

private void collectChildren(ITypeRoot unit, IJavaElement[] elements, ArrayList<SymbolInformation> symbols)
private void collectChildren(ITypeRoot unit, IJavaElement[] elements, ArrayList<SymbolInformation> symbols,
IProgressMonitor monitor)
throws JavaModelException {
for(IJavaElement element : elements ){
if (monitor.isCanceled()) {
return;
}
if(element instanceof IParent){
collectChildren(unit, filter(((IParent)element).getChildren()), symbols);
collectChildren(unit, filter(((IParent) element).getChildren()), symbols, monitor);
}
if(element.getElementType() != IJavaElement.FIELD &&
element.getElementType() != IJavaElement.METHOD
Expand Down Expand Up @@ -106,17 +120,6 @@ private boolean isSyntheticElement(IJavaElement element) {
}
}

public CompletableFuture<List<? extends SymbolInformation>> documentSymbol(DocumentSymbolParams params){
return CompletableFuture.supplyAsync(()->{
ITypeRoot unit = JDTUtils.resolveTypeRoot(params.getTextDocument().getUri());
if(unit == null ) {
return Collections.emptyList();
}
SymbolInformation[] elements = this.getOutline(unit);
return Arrays.asList(elements);
});
}

public static SymbolKind mapKind(IJavaElement element) {
switch (element.getElementType()) {
case IJavaElement.ANNOTATION:
Expand Down
Loading

0 comments on commit 277ee17

Please sign in to comment.