abingham / emacs-ycmd

Emacs client for ycmd, the code completion system.
MIT License
384 stars 46 forks source link

Company mode popup gets pushed right. #64

Closed trishume closed 9 years ago

trishume commented 9 years ago

In some cases when using company-ycmd, the first character will work great but on typing additional characters the popup will get pushed down and to the right.

For me this only occurs with ycmd, company works fine everywhere else. This happens in both Python and C++ mode and occurs with error buttons disabled and enabled. Not sure about other factors in my config that could cause this, I'll keep looking into it.

Screencast: http://cl.ly/2s1F1A2r3l08

Screenshot: screen shot 2014-11-05 at 9 03 34 pm

abingham commented 9 years ago

My initial guess is that this has something to do with company-mode and how it decides where to place things. But it may well be that the ycmd backend is flawed somehow.

Have you checked with the company-mode project to see if this behavior is symptomatic of something we might be doing wrong?

Also, can you post any company-mode configuration you've got that might be relevant?

trishume commented 9 years ago

It may well be a bug in company mode, if it is it would be nice to figure out what in ycmd is aggravating it that no other backend does.

I just tested and this occurs regardless of if the preview frontend is on, I thought it might be invisible preview text that pushed it over, but nope.

My Company config is here: https://github.com/trishume/spacemacs/blob/company-contrib/contrib/company-mode/packages.el

trishume commented 9 years ago

I just found a company-mode issue that displays this symptom but for a different trigger.

Tested and this also displays the behaviour noted in that issue that this does not happen there is whitespace after the current cursor position.

abingham commented 9 years ago

So can I consider this closed?

trishume commented 9 years ago

I assume you can't replicate the problem?

If not this must be a 3 way interaction between emacs-ycmd, company-mode and my specific emacs configuration (https://github.com/syl20bnr/spacemacs).

I'm going to attempt to fix this by adding a whitespace character after the insertion point when the company popup opens and deleting it when it closes. Totally a hack but that should fix it, even though I will still have no idea what the cause is.

abingham commented 9 years ago

Correct, I haven't been able to reproduce this behavior. When you mentioned the company-mode bug earlier, I thought you had narrowed it down to that. Sorry for the confusion.

I'll keep this open for now. Maybe I (or someone) will be able to grab your config, replicate the error, and debug it.

trishume commented 9 years ago

Yah, the thing about the company bug I referenced is that it is closed. The thing that triggered it in that bug was some weird interaction with flyspell.

Now some weird interaction with something else is triggering the exact same symptom. I'm currently trying to figure it out right now.

syl20bnr commented 9 years ago

One way to track this bug down would be to reproduce it with the Flyspell config since we know that Flyspell triggers the bug. Say enable company mode in text major-mode (should enable Flyspell automatically). We can start from here looking at what Flyspell does after C-g.

trishume commented 9 years ago

The bug with flyspell interaction was fixed.

Anyway by fiddling with the company-ycmd code I think I have narrowed it down to the fact that company-ycmd is my only async backend. I can replace the company-ycmd candidates method with something that uses the same deferred structure but just returns '(wow so complete) and the bug still happens.

trishume commented 9 years ago

Hmmm, after further debugging I have a theory. I think it might have to do with the deferred library wrecking some kind of context that company-mode expects.

Note how the bug I referenced was caused by flyspell triggering company-mode when something called this-command wasn't set. Perhaps some kind of context like this-command isn't present when the cb callback function is called from the "deferred" block.

@abingham can you try updating your version of the deferred library? Perhaps it is a regression in a newer version that is the trigger that I have that you don't.

syl20bnr commented 9 years ago

Did you have open an issue on the company side ? We can then reference these issues and bring more people to the table.

trishume commented 9 years ago

Nah, I've only commented on the closed one.

Also I just confirmed my hypothesis. I've commented out pretty much everything in company-ycmd except the async deferred part and the bug still happens, but when I just directly call the async callback (without deferred) it works.

Modified company-ycmd minimal-ish test case: http://hastebin.com/moqatifude.lisp

Once I get back from class I'll submit an issue to company-mode about broken deferred interaction, it would be nice if I knew why @abingham doesn't get the same problem when using deferred though.

dgutov commented 9 years ago

The problem with flyspell was very specific (see the comment added in the commit that closed that issue). If emacs-deferred calls sit-for, that should be quite surprising.

dgutov commented 9 years ago

Modified company-ycmd minimal-ish test case:

I've tried this not-really-minimal test case, and couldn't see the problem behavior. When you submit the issue, please include your Emacs version, and steps to reproduce it starting with emacs -Q.

trishume commented 9 years ago

@dgutov Yah sorry about that. I'd already realized that it has to do with some other interaction with my emacs config. The thing is I don't know which part it is and the config is HUGE.

It might be possible for someone to reproduce my config by cloning this branch into .emacs.d: https://github.com/trishume/spacemacs/tree/company-ycmd Then adding something like this to ~/.spacemacs:

(setq-default dotspacemacs-configuration-layers '(company-mode))

(setq-default dotspacemacs-excluded-packages
              '(jedi auto-complete-clang auto-complete ac-ispell tern-auto-complete ensime edts))
(defun dotspacemacs/init ()
  (setq-default ycmd-server-command '("python" "/path/to/ycmd/ycmd"))
)

However, I can't reasonably expect anybody (perhaps even including myself, but certainly not anybody else) to try and replicate my setup then debug the exact 3 way interaction among hundreds of packages in an asynchronous environment that is causing this.

So instead I'm trying out company-clang and irony-mode to see if they can do the job for me instead.

syl20bnr commented 9 years ago

@trishume Tell me what packages are mandatory for your setup and I'll see if I can setup a minimal config. We have to start from there, not the other way around with the 130+ packages of spacemacs.

trishume commented 9 years ago

The thing is my company-mode and company-ycmd setup is pretty vanilla, I'm pretty sure it is an unknown one of the other packages that is causing the issue. The thing is it doesn't seem to be any of the likely suspects, I disabled evil, smartparens, and all the non-company minor modes I could see in my modeline and the problem still occured. I see two ways to resolve this:

  1. Under the assumption that it is exactly one package causing the issue: binary search the package list. Disable half the packages and then recurse based on if the problem still happens. This might not even work for all I know.
  2. Do the hacky fix since it only seems to affect me anyway. I'll just figure out how to hook into company-mode and I'll add a single trailing space to the line when company-mode activates. I already have emacs set to remove trailing whitespace on save and I already know that a space after the completion point stops the symptom.

I'm going to work on the hacky fix tomorrow (Saturday) and if that doesn't work I might try binary search myself. I don't expect anyone else to spend a bunch of their free time helping me with a bug that only affects me.

trishume commented 9 years ago

Ok I decided just to switch to company-clang instead, since it actually has all the features I need. It's a bit slower but it has caching so at least the popup doesn't flash like ycmd. I've already hooked it up to load .clang_complete files and share those flags with flycheck.

So I don't plan on working anymore to fix this bug, and since nobody else experiences this bug you can close it if you want. Or you can leave it open because the bug actually still exists even though nobody is experiencing it.

dgutov commented 9 years ago

ensime/ensime-server#754 was a similar bug, caused by the implementation calling the asynchronous callback several times. @abingham, is there a chance that you did/do that, too?

Anyway, hopefully the latest commit in company-mode removes that flaw.

trishume commented 9 years ago

@dgutov thanks! I updated to the most recent version of company-mode and emacs-ycmd now works perfectly!