29
29
; ; from https://vxlabs.com/2018/11/19/configuring-emacs-lsp-mode-and-microsofts-visual-studio-code-python-language-server/
30
30
31
31
; ;; Code:
32
+ (require 'cl )
32
33
33
34
(defvar lsp-python-ms-dir nil
34
- " Path to langeuage server directory containing
35
- Microsoft.Python.LanguageServer.dll" )
35
+ " Path to langeuage server directory containing Microsoft.Python.LanguageServer.dll" )
36
36
37
37
(defvar lsp-python-ms-dotnet nil
38
38
" Full path to dotnet executable. You only need to set this if dotnet is not on your path." )
39
39
40
+ (defvar lsp-python-ms-executable nil
41
+ " Path to Microsoft.Python.LanguageServer.exe" )
42
+
40
43
; ; it's crucial that we send the correct Python version to MS PYLS,
41
44
; ; else it returns no docs in many cases furthermore, we send the
42
45
; ; current Python's (can be virtualenv) sys.path as searchPaths
43
46
44
47
(defun lsp-python-ms--get-python-ver-and-syspath (workspace-root )
45
- " return list with pyver-string and json-encoded list of python
48
+ " Return list with pyver-string and json-encoded list of python
46
49
search paths."
47
50
(let ((python (executable-find python-shell-interpreter))
48
51
(init " from __future__ import print_function; import sys; import json;" )
@@ -55,24 +58,31 @@ search paths."
55
58
; ; I based most of this on the vs.code implementation:
56
59
; ; https://github.com/Microsoft/vscode-python/blob/master/src/client/activation/languageServer/languageServer.ts#L219
57
60
; ; (it still took quite a while to get right, but here we are!)
58
- (defun lsp-python-ms--extra-init-params (workspace )
59
- (destructuring-bind (pyver pysyspath)
60
- (lsp-python-ms--get-python-ver-and-syspath (lsp--workspace-root workspace))
61
- `(:interpreter
62
- (:properties (
63
- :InterpreterPath ,(executable-find python-shell-interpreter)
64
- ; ; this database dir will be created if required
65
- :DatabasePath ,(expand-file-name (concat lsp-python-ms-dir " db/" ))
66
- :Version , pyver ))
67
- ; ; preferredFormat "markdown" or "plaintext"
68
- ; ; experiment to find what works best -- over here mostly plaintext
69
- :displayOptions (
70
- :preferredFormat " plaintext"
71
- :trimDocumentationLines :json-false
72
- :maxDocumentationLineLength 0
73
- :trimDocumentationText :json-false
74
- :maxDocumentationTextLength 0 )
75
- :searchPaths ,(json-read-from-string pysyspath))))
61
+ (defun lsp-python-ms--extra-init-params (&optional workspace )
62
+ (let ((workspace-root (if workspace (lsp--workspace-root workspace) (pwd ))))
63
+ (destructuring-bind (pyver pysyspath)
64
+ (lsp-python-ms--get-python-ver-and-syspath workspace-root)
65
+ `(:interpreter
66
+ (:properties (:InterpreterPath ,(executable-find python-shell-interpreter)
67
+ ; ; this database dir will be created if required
68
+ :DatabasePath ,(expand-file-name (concat lsp-python-ms-dir " db/" ))
69
+ :Version , pyver ))
70
+ ; ; preferredFormat "markdown" or "plaintext"
71
+ ; ; experiment to find what works best -- over here mostly plaintext
72
+ :displayOptions (:preferredFormat " plaintext"
73
+ :trimDocumentationLines :json-false
74
+ :maxDocumentationLineLength 0
75
+ :trimDocumentationText :json-false
76
+ :maxDocumentationTextLength 0 )
77
+ :searchPaths ,(json-read-from-string pysyspath)))))
78
+
79
+ (defun lsp-python-ms--client-initialized (client )
80
+ " Callback for client initialized."
81
+ (lsp-client-on-notification client " python/languageServerStarted" 'lsp-python-ms--language-server-started ))
82
+
83
+ (defun lsp-python-ms--language-server-started (workspace params )
84
+ " Callback for server started initialized."
85
+ (message " [MS Python language server started] " ))
76
86
77
87
(defun lsp-python-ms--workspace-root ()
78
88
" Get the root using ffip or projectile, or just return `default-directory' ."
@@ -83,12 +93,15 @@ search paths."
83
93
84
94
(defun lsp-python-ms--find-dotnet ()
85
95
" Get the path to dotnet, or return `lsp-python-ms-dotnet' ."
86
- (let ((dotnet (executable-find " dotnet" )))
96
+ (let ((dotnet (if ( eq system-type 'windows-nt ) " dotnet " ( executable-find " dotnet" ) )))
87
97
(if dotnet dotnet lsp-python-ms-dotnet)))
88
98
89
99
(defun lsp-python-ms--filter-nbsp (str )
90
100
" Filter nbsp entities from STR."
91
- (replace-regexp-in-string " " " " str))
101
+ (let ((rx " " ))
102
+ (when (eq system-type 'windows-nt )
103
+ (setq rx (concat rx " \\ |\r " )))
104
+ (replace-regexp-in-string rx " " str)))
92
105
93
106
94
107
(defun lsp-python-ms--language-server-started-callback (workspace params )
@@ -109,18 +122,40 @@ search paths."
109
122
(advice-add 'lsp-ui-doc--extract
110
123
:filter-return #'lsp-python-ms--filter-nbsp )
111
124
112
- ; ; lsp-ui-sideline--format-info gets called when lsp-ui wants to show hover info in the sideline
113
- ; ; again has to be removed
125
+ ; ; lsp-ui-sideline--format-info gets called when lsp-ui wants to show
126
+ ; ; hover info in the sideline again has to be removed
114
127
(advice-add 'lsp-ui-sideline--format-info
115
128
:filter-return #'lsp-python-ms--filter-nbsp )
116
129
117
- (lsp-define-stdio-client
118
- lsp-python " python"
119
- #'lsp-python-ms--workspace-root
120
- `(,(lsp-python-ms--find-dotnet) ,(concat lsp-python-ms-dir " Microsoft.Python.LanguageServer.dll" ))
121
- :extra-init-params #'lsp-python-ms--extra-init-params
122
- :initialize 'lsp-python-ms--client-initialized )
130
+ (defun lsp-python-ms--command-string ()
131
+ " Return the command that starts the server."
132
+ (if lsp-python-ms-executable
133
+ lsp-python-ms-executable
134
+ (list (lsp-python-ms--find-dotnet)
135
+ (concat lsp-python-ms-dir " Microsoft.Python.LanguageServer.dll" ))))
136
+
137
+ ; ;; Old lsp-mode
138
+ (unless (fboundp 'lsp-register-client )
139
+ (lsp-define-stdio-client
140
+ lsp-python " python"
141
+ #'lsp-python-ms--workspace-root
142
+ nil
143
+ :command-fn 'lsp-python-ms--command-string
144
+ :extra-init-params #'lsp-python-ms--extra-init-params
145
+ :initialize #'lsp-python-ms--client-initialized ))
146
+
147
+ ; ;; New lsp-mode
148
+ (when (fboundp 'lsp-register-client )
149
+ (lsp-register-client
150
+ (make-lsp-client
151
+ :new-connection (lsp-stdio-connection 'lsp-python-ms--command-string )
152
+ :major-modes '(python-mode )
153
+ :server-id 'mspyls
154
+ :initialization-options 'lsp-python-ms--extra-init-params
155
+ :notification-handlers (lsp-ht (" python/languageServerStarted" 'lsp-python-ms--language-server-started ))
156
+ )))
157
+
123
158
124
159
(provide 'lsp-python-ms )
125
160
126
- ; ;; lsp-python.el ends here
161
+ ; ;; lsp-python-ms .el ends here
0 commit comments