Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

best way to pass schema in nvim via LanguageClientNeovim #56

Closed
hurricanehrndz opened this issue Mar 16, 2018 · 43 comments
Closed

best way to pass schema in nvim via LanguageClientNeovim #56

hurricanehrndz opened this issue Mar 16, 2018 · 43 comments
Labels

Comments

@hurricanehrndz
Copy link

Just wondering what would be the best way to define new schemas using neovim and LanguageClient

@gorkem
Copy link
Collaborator

gorkem commented Mar 16, 2018

I am not familiar enough to neovim to provide a recommendation. If you can be more specific on the question we can help.

@hurricanehrndz
Copy link
Author

Under the readme you have the following:

Language Server Settings

yaml.schemas: The entrance point for new schema.

yaml.schemas: {
    "url": "globPattern",
    "kubernetes": "globPattern",
    "kedge": "globPattern"
}

I'm guess that is to configure vscode though, is it not?

@gorkem
Copy link
Collaborator

gorkem commented Mar 19, 2018

It is not VSCode specific, if the client (neovim) sends those settings using the didChangeConfiguration call to the server YAML server will react to it. VSCode actually issues that call to initialize the configuration right after the server is started and everytime settings are changed.

@hurricanehrndz hurricanehrndz changed the title best way to pass scheam in nvim via LanguageClientNeovim best way to pass schema in nvim via LanguageClientNeovim Mar 23, 2018
@hurricanehrndz
Copy link
Author

thank you so much @gorkem , I will post a minimal neovim config once I get it working.

@hurricanehrndz
Copy link
Author

@gorkem

Seems like this will not work due to your protocol extension custom/schema/request.

@gorkem
Copy link
Collaborator

gorkem commented Mar 24, 2018

What exactly is the behavior? If providing a url for a schema through settings (via didChangeConfiguration) is not working that is a bug. What are the values that you are passing to didChangeConfiguration?
/CC @JPinkney

@hurricanehrndz
Copy link
Author

Here is a log of the client
LanguageClient.log
In line 68 you will notice

{"jsonrpc":"2.0","method":"workspace/didChangeConfiguration","params":{"buftype":"","languageId":"yaml","settings":{"yaml
    .schemas":{"file:///home/hurricanehrndz/.config/nvim/yaml/schemas/ansible.json":"/*.yml"}}}}

In line 128 of the the rpchandler.
You will notice that buftype and languageid get dropped and the settings parm is the only thing sent.

In the following issue you will find a minimal vim environment and my test steps.

@hurricanehrndz
Copy link
Author

Here is a gif that might shed some light with what is going on.
peek 2018-03-25 21-29

@JPinkney
Copy link
Contributor

Thanks for all the info! I'm going to take a look at this tomorrow morning and see if I can find out whats going on.

@JPinkney
Copy link
Contributor

I've spotted one difference between the VSCode trace and that one. In the VSCode params when doing the didChangeConfiguration I get:

"settings": {
        "yaml": {
            "trace": {
                "server": "verbose"
            },
            "schemas": {
                "kubernetes": "/test.yaml"
            },
            "format": {
                "enable": true
            },
            "validate": true
        },
        "http": {
            "proxyStrictSSL": true
        }
 }

Whereas in your didChangeConfiguration there is:

{ "settings": 
  {
    "yaml.schemas": {"file:///home/hurricanehrndz/.config/nvim/yaml/schemas/ansible.json":"/*.yml"}
  }
}

In this case yaml isn't an object itself, instead yaml.schemas is the name of the object which would make sense why the settings.yaml.schemas is failing.

@hurricanehrndz
Copy link
Author

hurricanehrndz commented Mar 26, 2018 via email

@hurricanehrndz
Copy link
Author

hurricanehrndz commented Mar 26, 2018 via email

@JPinkney
Copy link
Contributor

If you install YAML Support by Red Hat in VSCode and then go into preferences look for yaml.trace.server and then change that to setting to be verbose. Then you will see all the results of whats send between the client and server!

@hurricanehrndz
Copy link
Author

It seems vscode also sends a json/schemaAssociations notification after initialization. I am betting that completion doesn't work without this notification? I'm not sure if it will be feasible to use this language server with the neovim clients, without developing something to aid.

@hurricanehrndz
Copy link
Author

Looking at how che does it, it seems that they launch the server with the preferences and then push the schema associations
https://github.com/eclipse/che/blob/master/plugins/plugin-yaml/che-plugin-yaml-server/src/main/java/org/eclipse/che/plugin/yaml/server/languageserver/YamlService.java
Is that right/

@JPinkney
Copy link
Contributor

It seems vscode also sends a json/schemaAssociations notification after initialization. I am betting that completion doesn't work without this notification?

It shouldn't need that notification thats just used to add schemas from the package.json https://github.com/redhat-developer/vscode-yaml/blob/master/src/extension.ts#L62

Out of curiosity do you mind trying this schema. Also, is it just autocompletion not working or are things like validation not working as well?

@hurricanehrndz
Copy link
Author

Thanks for the feekback no luck, it always terminates with the following error on client side:

2018-03-26T18:29:59.922329250-06:00 INFO languageclient::vim - <= {"jsonrpc":"2.0","id":5,"method":"custom/schema/request","params":"file:///home/hurricanehrndz/.travis.yml"}
2018-03-26T18:29:59.922818945-06:00 ERROR languageclient::vim - Error handling message. Message: {"jsonrpc":"2.0","id":5,"method":"custom/schema/request","params":"file:///home/hurricanehrndz/.travis.yml"}. Error: ErrorMessage { msg: "Invalid message of id: Num(5)" }

On server side it looks like this
peek 2018-03-26 18-12
It exits at line 177 from server.ts via jsonSchemaService.ts line 522

@hurricanehrndz
Copy link
Author

hurricanehrndz commented Mar 28, 2018

Good news and bad news.
First the bad news, I suspect my issues with this language server are due to andxu/yaml-language-server@eeb8987.
Good news is that if I revert to version prior to the commit, say 0.0.7, things work as expected.
peek 2018-03-27 19-33

I suspect that the schema never gets resolved.

For my vim config I'm doing the following.

function! SetYamlLangServerSchema(schema)
        echom "Using " . a:schema . " schema"
        let config = json_decode(system("cat ~/.config/nvim/yaml/" . a:schema . ".json"))
        call LanguageClient#Notify('workspace/didChangeConfiguration', { 'settings': config })
        let schemas = json_decode(join(readfile($HOME . "/schemas.json"), "\n"))
        call LanguageClient#Notify('json/schemaAssociations', schemas)
endfunction

As you can see completion and validation both work fine. I believe the custom schema provider is not something native the Language Server Protocol. I believe all language client wishing to implement this language server need to adhere to the custom/schema/request.

If you wish, I can provide my full minimal vim config that is used for testing and steps to reproduce success or issues.

For now I'm going to try and focus my efforts on debugging the schema resolution, since it seems to reference the customschemaprovider as well.

@languitar
Copy link

Any way to resolve this? I hit this as well.

@JPinkney
Copy link
Contributor

I think we will have to have the client register that they support the custom schema provider feature. In this case, I will make the custom schema provider feature off by default so that clients that don't/won't need that don't get blocked.

@languitar
Copy link

But in case a client doesn't have that custom extensions, can't the schema simply be loaded from disk directly by the server implementation?

@JPinkney
Copy link
Contributor

IIRC the custom schema provider is only used for when you want to add schemas programmically instead of doing it through workspace/didChangeConfiguration. Otherwise the schemas are loading normally though workspace/didChangeConfiguration which then loads the schema.

@hurricanehrndz
Copy link
Author

@JPinkney

Yes. When I did my deep dive into the code, the custom schema provider is used only when the schema definitions are defined within the ide and want to submit the schemas via the custom/schema/request from the yaml ls. Yaml ls should not crash and should continue to work without the client responding to this request.

Am I to understand that you no longer need to respond to this request?

@languitar
In terms of languageclient-neovim you should be able to respond to the custom request ("custom/schema/request") now via a registered handler. Read the documentation for clarification:
https://github.com/autozimu/LanguageClient-neovim/blob/next/doc/LanguageClient.txt#L516-L525

@languitar
Copy link

@hurricanehrndz Tried that, but the neovim implementation still complains about those requests as being unparseable:

17:10:11 INFO reader-yaml.ansible src/vim.rs:380 <= Some("yaml.ansible") {"jsonrpc":"2.0","id":2,"method":"custom/schema/request","params":"file:///home/languitar/src/server-configuration/site.yml"}
17:10:11 ERROR reader-yaml.ansible src/vim.rs:385 Failed to deserialize output: data did not match any variant of untagged enum RawMessage

 Message: {"jsonrpc":"2.0","id":2,"method":"custom/schema/request","params":"file:///home/languitar/src/server-configuration/site.yml"}

Error: Error("data did not match any variant of untagged enum RawMessage", line: 0, column: 0)

Anyway, why do I still need this? Why doesn't setting the configuration options work correctly?

@hurricanehrndz
Copy link
Author

Setting configuration options has always worked. I never had an issue with that. The problem was always with YAML LS not doing completions if you didn't respond to the custom request. As long as you respond to the custom request completion should work, it just needs to be a blank response. I would not pass custom schema via the request, I always did that via notify. I have not tested the responding the request, but that is because the last time I used this the handler functionality of the language client did not exist. So it is up to you to test it out.

You can see that here:
https://github.com/hurricanehrndz/nvim/blob/master/autoload/hurricane/yamlLS.vim

I wrote a basic config example and everything on the wiki for the language-client:
https://github.com/autozimu/LanguageClient-neovim/wiki/yaml-language-server

@hurricanehrndz
Copy link
Author

hurricanehrndz commented Sep 19, 2018

@languitar

on why we need to respond to the request, I personally have no idea.

@JPinkney had mentioned awhile ago that YAML LS would be updated to have clients report support for the custom request, so that clients who do not respond do not get blocked.

Whether this has been implemented or not, only he can answer.

@JPinkney
Copy link
Contributor

had mentioned awhile ago that YAML LS would be updated to have clients report support for the custom request, so that clients who do not respond do not get blocked.

Whether this has been implemented or not, only he can answer.

Hasn't been implemented yet but I'm hoping to get to it next week.

@languitar
Copy link

That would be great, because answering the custom request still doesn't work with the neovim client. The reason is that the payload of the request (params) is a string, but the specification of the protocol says:

params?: Array<any> | object;

@JPinkney if you start changing things here, maybe fixing that to an object or array would also be a good idea to be consistent with the protocol specification.

@JPinkney
Copy link
Contributor

JPinkney commented Oct 1, 2018

I've made it so clients have to register that they want to use "custom/schema/request". Please give the newest version a try and let me know if it works for you!

@languitar
Copy link

Just starting to test this. First thing I get is:

[Error] Notification handler 'workspace/didChangeConfiguration' failed with message: Cannot read property 'singleQuote' of undefined

@languitar
Copy link

Here is the complete communication up to that error:

Content-Length: 377

{"jsonrpc":"2.0","method":"initialize","params":{"capabilities":{"textDocument":{"completion":{"completionItem":{"snippetSupport":true}}},"workspace":{"applyEdit":true,"didChangeWatchedFiles":{"dynamicRegistration":true}}},"processId":3830,"rootPath":"/home/languitar/src/server-configuration","rootUri":"file:///home/languitar/src/server-configuration","trace":"off"},"id":34}Content-Length: 206

{"jsonrpc":"2.0","id":34,"result":{"capabilities":{"textDocumentSync":1,"completionProvider":{"resolveProvider":true},"hoverProvider":true,"documentSymbolProvider":true,"documentFormattingProvider":false}}}Content-Length: 52

{"jsonrpc":"2.0","method":"initialized","params":{}}Content-Length: 361

{"jsonrpc":"2.0","method":"workspace/didChangeConfiguration","params":{"settings":{"settings":{"yaml":{"schemas":{"http://json.schemastore.org/ansible-stable-2.5":"*.yml"},"validate":true},"yaml.schemas":{"http://json.schemastore.org/ansible-stable-2.5":"*.yml"}},"yaml":{"schemas":{"http://json.schemastore.org/ansible-stable-2.5":"/*.yml"},"validate":true}}}}Content-Length: 203

{"jsonrpc":"2.0","method":"window/logMessage","params":{"type":1,"message":"Notification handler 'workspace/didChangeConfiguration' failed with message: Cannot read property 'singleQuote' of undefined"}}Content-Length: 2984

@JPinkney
Copy link
Contributor

JPinkney commented Oct 2, 2018

I wonder if the language server is crashing because of the new settings https://github.com/redhat-developer/yaml-language-server#language-server-settings

@languitar
Copy link

languitar commented Oct 2, 2018

Looks like there is some hidden assumption about the settings always being sent to the server from the client in the initialize request.

@languitar
Copy link

One I add a "format" object to the settings, this works. So there is a missing check for that object to exist.

@JPinkney
Copy link
Contributor

If I'm not mistaken everything here should be good to go now. Let me know if there are any more issues.

@nkakouros
Copy link

I am having a hard time making the language server work with LanguageClient-neovim. After I read the comments on this issue, I configured the following.

I have an ansible.json file that I pass to the language server:

{
  "yaml": {
    "format": {
     "enable": false
    },
    "validate": true,
    "hover": true,
    "completion": true,
    "schemas": {
      "file:///path/to/ansible/schema.json": "/*"
    }
  },
  "http": {
    "proxyStrictSSL": true
  }
}

I am using this to send the above json stuff to the language server:

    call LanguageClient#Notify('workspace/didChangeConfiguration', { 'settings': config })

where config is the above json data.

Then, I have registered a handler for custom/schema/request:

  call LanguageClient#registerHandlers({
    \ 'custom/schema/request': 'HandleWorkspaceConfig',
  \ })

and the handler simply runs:

    call LanguageClient#Notify('custom/schema/request', '')

The weird thing is that in the log generated by LanguageClient, there is no custom/schema/request being received by it. What am I missing?

@JPinkney
Copy link
Contributor

You shouldn't need to do custom/schema/request. If I'm not mistaken its only needed for VSCode specifically for a few extensions that are build off of https://github.com/redhat-developer/vscode-yaml

@nkakouros
Copy link

OK. But I do not get any completions.

I forgot to mention that I start the language server with:

node ~/.local/npm-global/lib/node_modules/yaml-language-server/out/server/src/server.js --stdio

I am getting some diagnostic feedback for malformed yaml so communication with the server does happen successfully.

From the logs of the client, I see this:

20:54:47 INFO writer-Some("yaml.ansible") src/rpcclient.rs:216 => Some("yaml.ansible") {"jsonrpc":"2.0","method":"textDocument/completion","params":{"position":{"character":9,"line":32},"textDocument":{"uri":"file:///home/nikos/Projects/Ethical%20Hacking/EN2720/plays/instances/gibson.yml"}},"id":6}
20:54:47 INFO reader-Some("yaml.ansible") src/rpcclient.rs:170 <= Some("yaml.ansible") {"jsonrpc":"2.0","id":6,"result":{"items":[],"isIncomplete":false}}
20:54:47 INFO writer-None src/rpcclient.rs:216 => None {"jsonrpc":"2.0","result":{"isIncomplete":false,"items":[]},"id":5}

@nkakouros
Copy link

Actually, I can't get this to work at all even with vscode. I uninstalled any manual installation of yaml-language-server (npm uninstall -g yaml-language-server) and then, in vscode, I installed the yaml extension and added to my settings:

  "yaml.schemas": {
    "kubernetes": "/*.yml"
  }

Then, I created a new .yml file and pressed Ctrl+Space. I got no completions. I tried loading the ansible schema, but failed to get completions again. I added "yaml.completion": true to the settings, but still got nothing. I am other too noob with language servers or I am understanding sth wrong. How does one get completions with this language server?

@JPinkney
Copy link
Contributor

In the preferences can you make yaml.trace.server be verbose and then in the output tab of vscode make sure the YAML support tab is selected
Screen Shot 2019-03-10 at 5 59 04 PM
then paste in the contents of the output because using that configuration works for me on 1.32.1

@nkakouros
Copy link

So, started from scratch and managed to get kubernetes working. These are all the custom vscode settings that I have:

{
  "yaml.schemas": {
    "kubernetes": "/*.yml"
  },
  "yaml.trace.server": "verbose"
}

Now, if I change kubernetes to /home/me/.config/nvim/misc/yaml-schemas/ansible.json or http://json.schemastore.org/ansible-stable-2.5 then I get no completions. Also, I get some wrong errors that the following:

- hosts: all
  tasks:
    ...

needs fixing because a shell property is missing:

- hosts: all
  shell: whatever
  tasks:
    ...

But even after that, no completion happens. I guess there is sth wrong with the schema file?

@JPinkney
Copy link
Contributor

For http://json.schemastore.org/ansible-stable-2.5 schema you need to start with a - and then a space and then you should getting completions. If you get completions/hover/schema validation at least once then that means the schema is setup correctly. If you're getting further issues that look to be schema issues you can report them here

@nkakouros
Copy link

OK, I think I am finally getting somewhere. Sincere thanks for your help and even more you patience. 🙇‍♂️

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

5 participants