Skip to content

Commit d282ee9

Browse files
authored
OCaml client: Add inferIntf and some fixes (#4899)
See https://github.com/ocaml/ocaml-lsp/blob/master/ocaml-lsp-server/docs/ocamllsp/inferIntf-spec.md for more informations.
1 parent fc1af42 commit d282ee9

File tree

2 files changed

+48
-4
lines changed

2 files changed

+48
-4
lines changed

clients/lsp-ocaml.el

Lines changed: 47 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -122,8 +122,7 @@
122122
123123
OCaml-lsp custom protocol documented here
124124
https://github.com/ocaml/ocaml-lsp/blob/master/ocaml-lsp-server/docs/ocamllsp/switchImplIntf-spec.md"
125-
(-if-let* ((params (lsp-make-ocaml-lsp-switch-impl-intf-params
126-
:uri (lsp--buffer-uri)))
125+
(-if-let* ((params (make-vector 1 (lsp--buffer-uri)))
127126
(uris (lsp-request "ocamllsp/switchImplIntf" params)))
128127
uris
129128
(lsp--warn "Your version of ocaml-lsp doesn't support the switchImplIntf extension")))
@@ -158,6 +157,18 @@ https://github.com/ocaml/ocaml-lsp/blob/master/ocaml-lsp-server/docs/ocamllsp/ge
158157
(lsp-request "ocamllsp/getDocumentation" params)
159158
(lsp--warn "Your version of ocaml-lsp doesn't support the getDocumentation extension")))
160159

160+
(defun lsp-ocaml--infer-intf ()
161+
"Infer the interface of the given URI.
162+
163+
The URI should correspond to an implementation file, not an interface one.
164+
165+
OCaml-lsp protocol is documented here:
166+
https://github.com/ocaml/ocaml-lsp/blob/master/ocaml-lsp-server/docs/ocamllsp/inferIntf-spec.md"
167+
(-if-let* ((params (make-vector 1 (lsp--buffer-uri)))
168+
(result (lsp-request "ocamllsp/inferIntf" params)))
169+
result
170+
(lsp--warn "Your version of ocaml-lsp doesn't support the inferIntf extension")))
171+
161172
;;; -------------------
162173
;;; OCaml-lsp general utilities
163174
;;; -------------------
@@ -170,6 +181,15 @@ https://github.com/ocaml/ocaml-lsp/blob/master/ocaml-lsp-server/docs/ocamllsp/ge
170181
;;; OCaml-lsp URI utilities
171182
;;; -------------------
172183

184+
(defun lsp-ocaml--is-interface (uri)
185+
"Return non-nil if the given URI is an interface, nil otherwise."
186+
(let ((path (lsp--uri-to-path uri)))
187+
(string-match-p "\\.\\(mli\\|rei\\|eliomi\\)\\'" path)))
188+
189+
(defun lsp-ocaml--on-interface ()
190+
"Return non-nil if the current URI is an interface, nil otherwise."
191+
(lsp-ocaml--is-interface (lsp--buffer-uri)))
192+
173193
(defun lsp-ocaml--load-uri (uri &optional other-window)
174194
"Check if URI exists and open its buffer or create a new one.
175195
@@ -328,6 +348,31 @@ If TYPE is a single-line that represents a module type, reformat it."
328348

329349
;;; The following functions are interactive implementations of the OCaml-lsp requests
330350

351+
(defun lsp-ocaml-infer-interface ()
352+
"Infer the interface for the current file."
353+
(interactive)
354+
(let* ((current-uri (lsp--buffer-uri))
355+
(intf-uri (if (lsp-ocaml--is-interface current-uri)
356+
current-uri
357+
(lsp-ocaml--find-alternate-uri)))
358+
(impl-uri (if (lsp-ocaml--is-interface current-uri)
359+
(lsp-ocaml--find-alternate-uri)
360+
current-uri))
361+
(intf-path (lsp--uri-to-path intf-uri))
362+
(impl-path (lsp--uri-to-path impl-uri)))
363+
(if (lsp-ocaml--load-uri impl-uri) ; the impl file needs to be loaded
364+
(when (y-or-n-p
365+
(format "Try to generate an interface for %s? " impl-path))
366+
(let ((result (lsp-ocaml--infer-intf)))
367+
(with-current-buffer (get-buffer-create intf-path)
368+
(when (or (= (buffer-size) 0)
369+
(y-or-n-p "The buffer is not empty, overwrite it? "))
370+
(erase-buffer)
371+
(insert result)
372+
;; Create the file if it doesn’t exist
373+
(unless (file-exists-p intf-path)
374+
(write-file intf-path)))))))))
375+
331376
(defun lsp-ocaml-find-alternate-file ()
332377
"Return the URI corresponding to the alternate file if there's only one or prompt for a choice."
333378
(interactive)

lsp-protocol.el

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -433,8 +433,7 @@ See `-let' for a description of the destructuring mechanism."
433433
(lsp-interface (csharp-ls:CSharpMetadata (:textDocument))
434434
(csharp-ls:CSharpMetadataResponse (:source :projectName :assemblyName :symbolName)))
435435

436-
(lsp-interface (ocaml-lsp:SwitchImplIntfParams (:uri) nil)
437-
(ocaml-lsp:TypeEnclosingParams (:uri :at :index :verbosity) nil)
436+
(lsp-interface (ocaml-lsp:TypeEnclosingParams (:uri :at :index :verbosity) nil)
438437
(ocaml-lsp:TypeEnclosingResult (:index :enclosings :type) nil)
439438
(ocaml-lsp:GetDocumentationParams (:textDocument :position :contentFormat) nil))
440439

0 commit comments

Comments
 (0)