Bug 350409 - [content assist] Extended Listener Support for Code Completion Interfaces
Summary: [content assist] Extended Listener Support for Code Completion Interfaces
Status: RESOLVED FIXED
Alias: None
Product: JDT
Classification: Eclipse Project
Component: Text (show other bugs)
Version: 3.7   Edit
Hardware: All All
: P3 enhancement with 8 votes (vote)
Target Milestone: 3.8 M6   Edit
Assignee: Dani Megert CLA
QA Contact:
URL:
Whiteboard:
Keywords: api
Depends on:
Blocks:
 
Reported: 2011-06-27 04:38 EDT by Marcel Bruch CLA
Modified: 2012-04-27 02:33 EDT (History)
7 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Marcel Bruch CLA 2011-06-27 04:38:17 EDT
Code Recommenders is working on various code completion engines. One of which is the subwords completion engine. Deepak asked me to bring this completion engine over to JDT (cf. bug #350000) which is IMHO a perfect place for it.

However, Code Recommenders doesn't stop with creating few new engines. We would like to track how people use code completion, i.e., when code completion was triggered, in which code context, what has been proposed, what has been selected, what proposals a user looked at etc. This enables us to create more interesting completion engines and tools not only related to code completion.  Think of it as an extension to the usage data collector but suited to build Code Recommenders vision of "IDE 2.0" (see http://goo.gl/DKOjW).

With our own completion engines we are able to track these events and learn valuable completions. This, however, would require us to keep these engines as part of Code Recommenders which is somewhat counterproductive. 

It would be great if JDT team could consider (i) to extend the current listener support for completion engines to allow us to plug-in our own listeners that do the book keeping of what has been proposed/viewed/selected and (ii) to open the JavaCompletionProposal hierarchy a bit to provide access to little more context information relevant for our tools.

This bug is somewhat related to bug 340945.

Any thoughts on that?
Comment 1 Dani Megert CLA 2011-07-04 07:06:51 EDT
I guess we could add some more API to org.eclipse.jface.text.contentassist.ICompletionListener.

I suggest you add a patch with the changes you have in mind. We can then discuss whether they are acceptable or not.
Comment 2 Marcel Bruch CLA 2012-01-22 16:34:37 EST
While discussing new approaches to ranking code completion proposals, it became obvious to me that adding more and more completion engines to JDT is not the right approach. Here is a simple, easy to implement yet powerful approach that would enable us to provide an amazing feature-set on JDT's code completion in a non-intrusive way.

What I have in mind is this:


1. Add this new interface so the completion proposal sorter framework:

public interface IProposalSorterExtension2 {
   void transform( List<ICompletionProposal> proposals);
}

2. Modify ProposalSorterHandle.sortProposals as follows:

sorter.beginSorting(context);
if (sorter instanceof IProposalSorterExtension2) {
  ((IProposalSorterExtension2) sorter).transform(proposals);
} else {
  Collections.sort(proposals, sorter);
}
sorter.endSorting();




Advantages over the existing solution:

1. Intelligent completion proposal computers don't create unneeded and confusing additional proposals but would just rank them according to their new relevance scheme.

2. Since AbstractJavaCompletion allows to setDisplayString(), the relevance sorter can also update the highlights (for instance for subwords completion to indicate which parts of the proposal matched the user-entered token).

3. Proposals can be grouped by some category (needs a special ICompletionProposalExtension interface)

4. Duplicates that may be introduced by ,e.g., subwords completion can be filtered easily.

5. Existing proposals can be decorated easily to track executions and user-interactions

6. ... Extensions to the listener interface are not needed with this approach, since the requested behavior can be added by some decorators or replacements of existing proposals.


The relevance sorter will be enabled using the existing org.eclipse.jdt.ui.javaCompletionProposalSorters extension point.

What do you think? To me this would open the completion framework in an extremely valuable for our approach and changes would be minimally intrusive.
Comment 3 Deepak Azad CLA 2012-01-31 06:26:05 EST
I have been using Subwords completion from Code Recommenders for a couple of weeks now, and I find it quite liberating as I can just type 'obj.elements' and I am offered all of the following in one go.
obj.getElement(..)
obj.findElements(..)
obj.createElements(..)

=> Easier to make a choice of what you want to do
=> Saves time!

However, the current implementation creates duplicate proposals when I type 'obj.getElement'. With the current infrastructure in JDT I guess these are unavoidable. The ability to 'transform' proposals offered by JDT does appear to be the right approach in this context (but then I have not looked at the code to know if there are any issues there)
Comment 4 Dani Megert CLA 2012-02-07 08:10:50 EST
Comment 2 seems to ask for different things than comment 0.

Re comment 0: see comment 1.

Re comment 2: What you're asking is a hook to basically hijack proposals from other processors under the umbrella of "sorting". Eclipse philosophy is to allow plug-ins to extend/add existing stuff and protect those contributions. That's why we always rejected any filtering mechanism/extension point.
Comment 5 Marcel Bruch CLA 2012-02-07 08:18:08 EST
(In reply to comment #4)
> Re comment 2: What you're asking is a hook to basically hijack proposals from
> other processors under the umbrella of "sorting". Eclipse philosophy is to
> allow plug-ins to extend/add existing stuff and protect those contributions.
> That's why we always rejected any filtering mechanism/extension point.

Proposal-Hijacking would be possible, although not intended. Do you expect this to be a real danger? I mean: how many extensions would jump in an hijack proposals and would blame JDT for this?

If filtering is no option, is decorating a existing proposal an option?
We'd like to get notified which proposal has been applied, looked at etc. Extending the listener interface seems to be more complex than decorating.

If decorating is also no option, what is the deadline for this having this extension in JDT 3.8?
Comment 6 Deepak Azad CLA 2012-02-07 08:21:43 EST
(In reply to comment #4)
> Re comment 2: What you're asking is a hook to basically hijack proposals from
> other processors under the umbrella of "sorting". Eclipse philosophy is to
> allow plug-ins to extend/add existing stuff and protect those contributions.
> That's why we always rejected any filtering mechanism/extension point.

Well.. sorting is extending the existing JDT 'relevance sort'. Currently we allow others to 'add' proposals to the default content assist list, and this is configurable. 'Rearranging' the proposals by extenders, with appropriate configuration options, is not much different from 'adding' extra proposals - both mechanisms can potentially mess up content assist which is what I guess you are afraid of.
Comment 7 Dani Megert CLA 2012-02-07 08:28:13 EST
(In reply to comment #5)
> (In reply to comment #4)
> > Re comment 2: What you're asking is a hook to basically hijack proposals from
> > other processors under the umbrella of "sorting". Eclipse philosophy is to
> > allow plug-ins to extend/add existing stuff and protect those contributions.
> > That's why we always rejected any filtering mechanism/extension point.
> 
> Proposal-Hijacking would be possible, although not intended. Do you expect this
> to be a real danger? I mean: how many extensions would jump in an hijack
> proposals and would blame JDT for this?

This happened. I won't provide names here. Fact is, the bugs would end up in our bucket and we'd have to figure out the things.


> If filtering is no option, is decorating a existing proposal an option?

What exactly do mean by "decorating"? Label? Store data?


> If decorating is also no option, what is the deadline for this having this
> extension in JDT 3.8?

Deadline is M6 - 3 weeks (around February 24).
Comment 8 Dani Megert CLA 2012-02-07 08:33:02 EST
(In reply to comment #6)
> (In reply to comment #4)
> > Re comment 2: What you're asking is a hook to basically hijack proposals from
> > other processors under the umbrella of "sorting". Eclipse philosophy is to
> > allow plug-ins to extend/add existing stuff and protect those contributions.
> > That's why we always rejected any filtering mechanism/extension point.
> 
> Well.. sorting is extending the existing JDT 'relevance sort'. Currently we
> allow others to 'add' proposals to the default content assist list, and this is
> configurable. 'Rearranging' the proposals by extenders, with appropriate
> configuration options, is not much different from 'adding' extra proposals -
> both mechanisms can potentially mess up content assist which is what I guess
> you are afraid of.

I'm not sure what you try to say here. I'm not against sorting (i.e. rearranging) or adding additional proposals with new processors (aka kinds). The user can choose what kind of proposals he likes to see and the processor/kind provider is responsible for the proposals. No API will ever be provided that changes this.
Comment 9 Marcel Bruch CLA 2012-02-07 09:08:13 EST
(In reply to comment #7)
> > If filtering is no option, is decorating a existing proposal an option?
> 
> What exactly do mean by "decorating"? Label? Store data?

Potentially all of them.
Instant use cases include but are not exhaustive:

* tracking which proposal has been applied, looked at,
* changing the label (e.g., appending a percentage value), and
* change proposal relevance (e.g., to re-rank according to other scoring systems).

The third option can be achieved with the relevance sorter. 1 and 2 can't. The only way around this would be to create a JavaAllCompletionsProposalComputer replacement.

> 
> > If decorating is also no option, what is the deadline for this having this
> > extension in JDT 3.8?
> 
> Deadline is M6 - 3 weeks (around February 24).

ouch.
Comment 10 Dani Megert CLA 2012-02-07 09:27:30 EST
(In reply to comment #9)
> (In reply to comment #7)
> > > If filtering is no option, is decorating a existing proposal an option?
> > 
> > What exactly do mean by "decorating"? Label? Store data?
> 
> Potentially all of them.
> Instant use cases include but are not exhaustive:
> 
> * tracking which proposal has been applied, looked at,

- Applied: you can already do this for your own proposals. If you need this
  in general, then this could be added to a listener extension.
- There's ICompletionListener.selectionChanged(ICompletionProposal, boolean)
  but to be hones I'm not sure how you want to measure "looked at".


> * changing the label (e.g., appending a percentage value), and
Nope, this is again hijacking a foreign processor ;-).

> * change proposal relevance (e.g., to re-rank according to other scoring
> systems).
You can do that for your own proposals. Changing the ranking for other processors will not happen.

 
> The third option can be achieved with the relevance sorter. 1 and 2 can't. The
> only way around this would be to create a JavaAllCompletionsProposalComputer
> replacement.

Correct. If you want full control, you have to provide the entire proposal computer and replace the existing one. There's API to do that, see org.eclipse.jdt.ui.PreferenceConstants.setExcludedCompletionProposalCategories(String[]).
Comment 11 Marcel Bruch CLA 2012-02-17 02:34:42 EST
(In reply to comment #10)

> If you want full control, you have to provide the entire proposal
> computer and replace the existing one. There's API to do that, see
> org.eclipse.jdt.ui.PreferenceConstants.setExcludedCompletionProposalCategories(String[]).

Given the impact these changes would have, I think it's easier to go with replacing. I tend towards making subwords a replacement of JDT's AllProposalsComputer and all the needed behavior there.

But given that engines like subwords and call-chain might potentially move to JDT, we'd like to see the Listener.applied(ICompletionProposal) because otherwise we'd loose an important learning mechanism to make code completion smarter over time.

Is adding an applied() extension still possible for 3.8?
Comment 12 Dani Megert CLA 2012-02-17 04:10:08 EST
> Is adding an applied() extension still possible for 3.8?
Fixed in master: 0cfb9b481be22e581b008d11f97ddbe249ce561d
Comment 13 Sebastian Proksch CLA 2012-04-26 09:40:16 EDT
I'm trying to implement a "completion tracker" that collects information about what was selected in the code completion. I had a look at the new org.eclipse.jface.text.contentassist.ContentAssistant but I'm not sure how to access it. What is the intended way to achieve this?

I expected that I could simply add a part listener to org.eclipse.jdt.internal.ui.javaeditor.CompilationUnitEditor like this one:

new IPartListener() {
  @Override
  public void partOpened(IWorkbenchPart p) {
    if (p instanceof CompilationUnitEditor) {
      CompilationUnitEditor cue = (CompilationUnitEditor) p;
      ISourceViewer sv = cue.getViewer();
      CompilationUnitEditor.AdaptedSourceViewer asv =
        (CompilationUnitEditor.AdaptedSourceViewer) sv;
      ContentAssistant ca =
        (ContentAssistant) asv.getContentAssistant();
      ca.addCompletionListener(...);
    }
  }
  ...
}

My problem is that the AdaptedSourceViewer has only package visible and therefore is not accessible by me. Is it possible to change its visibility to public or is there another way to get access to the ContentAssistant?
Comment 14 Dani Megert CLA 2012-04-26 10:19:12 EDT
(In reply to comment #13)
> My problem is that the AdaptedSourceViewer has only package visible and
> therefore is not accessible by me. Is it possible to change its visibility to
> public or is there another way to get access to the ContentAssistant?

org.eclipse.jface.text.source.SourceViewer.getContentAssistantFacade()
Comment 15 Sebastian Proksch CLA 2012-04-26 10:40:29 EDT
That worked. Thank you!
Comment 16 Sebastian Proksch CLA 2012-04-26 14:13:47 EDT
The method ICompletionListener.assistSessionEnded(...) seems to be called every time the proposal popup is going to hide. Is there a way to distinguish between a simple abort (e.g. by pressing escape) and an actual selection of a proposal?
Comment 17 Dani Megert CLA 2012-04-27 02:33:37 EDT
(In reply to comment #16)
> The method ICompletionListener.assistSessionEnded(...) seems to be called 
> every time the proposal popup is going to hide. 
Yes, that's how it is specified.

> Is there a way to distinguish between
> a simple abort (e.g. by pressing escape) and an actual selection of a 
> proposal?
You mean "insertion"? If so,  see ICompletionListenerExtension2.applied(ICompletionProposal)


Ah, and please stop abusing this bug to ask questions ;-)