From c765121f67df7f7cdc03e16b1130f4e508b39a98 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Jo=C3=A3o=20T=C3=A1vora?= Date: Tue, 22 May 2018 11:41:02 +0100 Subject: [PATCH] Introduce new api methods for experimental clients to use Should help Josh Elsasser implement pull request https://github.com/joaotavora/eglot/issues/6. * eglot.el (eglot--obj): Move upwards in file. (eglot-server-ready-p): Tweak comment. (eglot-initialization-options): New API defgeneric.. (eglot-client-capabilities): New API defgeneric. (eglot--client-capabilities): Remove. (eglot--connect): Call new API methods here. --- lisp/progmodes/eglot.el | 85 +++++++++++++++++++++-------------------- 1 file changed, 44 insertions(+), 41 deletions(-) diff --git a/lisp/progmodes/eglot.el b/lisp/progmodes/eglot.el index 43cda1b42ef..5e9bdc3566b 100644 --- a/lisp/progmodes/eglot.el +++ b/lisp/progmodes/eglot.el @@ -115,12 +115,19 @@ lasted more than that many seconds." ;;; API ;;; +(defmacro eglot--obj (&rest what) + "Make WHAT a JSON object suitable for `json-encode'." + (declare (debug (&rest form))) + ;; FIXME: not really API. Should it be? + ;; FIXME: maybe later actually do something, for now this just fixes + ;; the indenting of literal plists. + `(list ,@what)) + (cl-defgeneric eglot-server-ready-p (server what) ;; API "Tell if SERVER is ready for WHAT in current buffer. If it isn't, a deferrable `eglot--async-request' *will* be deferred to the future." - (:method (_s _what) - "Normally not ready if outstanding changes." + (:method (_s _what) "Normally ready if no outstanding changes." (not (eglot--outstanding-edits-p)))) (cl-defgeneric eglot-handle-request (server method id &rest params) @@ -129,6 +136,35 @@ deferred to the future." (cl-defgeneric eglot-handle-notification (server method id &rest params) "Handle SERVER's METHOD notification with PARAMS.") +(cl-defgeneric eglot-initialization-options (server) + "JSON object to send under `initializationOptions'" + (:method (_s) nil)) ; blank default + +(cl-defgeneric eglot-client-capabilities (server) + "What the EGLOT LSP client supports for SERVER." + (:method (_s) + (eglot--obj + :workspace (eglot--obj + :applyEdit t + :workspaceEdit `(:documentChanges :json-false) + :didChangeWatchesFiles `(:dynamicRegistration t) + :symbol `(:dynamicRegistration :json-false)) + :textDocument + (eglot--obj + :synchronization (eglot--obj + :dynamicRegistration :json-false + :willSave t :willSaveWaitUntil t :didSave t) + :completion `(:dynamicRegistration :json-false) + :hover `(:dynamicRegistration :json-false) + :signatureHelp `(:dynamicRegistration :json-false) + :references `(:dynamicRegistration :json-false) + :definition `(:dynamicRegistration :json-false) + :documentSymbol `(:dynamicRegistration :json-false) + :documentHighlight `(:dynamicRegistration :json-false) + :rename `(:dynamicRegistration :json-false) + :publishDiagnostics `(:relatedInformation :json-false)) + :experimental (eglot--obj)))) + ;;; Process management (defvar eglot--servers-by-project (make-hash-table :test #'equal) @@ -223,13 +259,6 @@ CONTACT is in `eglot'. Returns a process object." (let ((inhibit-read-only t)) (erase-buffer) (read-only-mode t))) proc)) -(defmacro eglot--obj (&rest what) - "Make WHAT a suitable argument for `json-encode'." - (declare (debug (&rest form))) - ;; FIXME: maybe later actually do something, for now this just fixes - ;; the indenting of literal plists. - `(list ,@what)) - (defun eglot--all-major-modes () "Return all know major modes." (let ((retval)) @@ -238,29 +267,6 @@ CONTACT is in `eglot'. Returns a process object." (push sym retval)))) retval)) -(defun eglot--client-capabilities () - "What the EGLOT LSP client supports." - (eglot--obj - :workspace (eglot--obj - :applyEdit t - :workspaceEdit `(:documentChanges :json-false) - :didChangeWatchesFiles `(:dynamicRegistration t) - :symbol `(:dynamicRegistration :json-false)) - :textDocument (eglot--obj - :synchronization (eglot--obj - :dynamicRegistration :json-false - :willSave t :willSaveWaitUntil t :didSave t) - :completion `(:dynamicRegistration :json-false) - :hover `(:dynamicRegistration :json-false) - :signatureHelp `(:dynamicRegistration :json-false) - :references `(:dynamicRegistration :json-false) - :definition `(:dynamicRegistration :json-false) - :documentSymbol `(:dynamicRegistration :json-false) - :documentHighlight `(:dynamicRegistration :json-false) - :rename `(:dynamicRegistration :json-false) - :publishDiagnostics `(:relatedInformation :json-false)) - :experimental (eglot--obj))) - (defvar eglot-connect-hook nil "Hook run after connecting in `eglot--connect'.") (defun eglot--connect (project managed-major-mode contact server-class) @@ -294,15 +300,12 @@ class SERVER-CLASS." (eglot--request server :initialize - (eglot--obj :processId (unless (eq (process-type proc) - 'network) - (emacs-pid)) - :capabilities(eglot--client-capabilities) - :rootPath (expand-file-name - (car (project-roots project))) - :rootUri (eglot--path-to-uri - (car (project-roots project))) - :initializationOptions [])) + (eglot--obj + :processId (unless (eq (process-type proc) 'network) (emacs-pid)) + :capabilities (eglot-client-capabilities) + :rootPath (expand-file-name (car (project-roots project))) + :rootUri (eglot--path-to-uri (car (project-roots project))) + :initializationOptions (eglot-initialization-options server))) (setf (eglot--capabilities server) capabilities) (setf (eglot--status server) nil) (dolist (buffer (buffer-list)) -- 2.39.2