Skip to content

Commit

Permalink
support cm* files (ocamllabs#798)
Browse files Browse the repository at this point in the history
- Add support for opening compilation artifacts in human-readable form in the
  editor (ocamllabs#798)

  Currently supported artifacts include `.cmi`, `.cmt(i)`, `.cmo`, `.cma`,
  `.cmx(a/s)`, and `.bc` files.

  To learn more about these files, see: https://ocaml.org/manual/comp.html

- Add bindings for `CustomDocument`, `FileSystemWatcher`, `Workspace.createFileSystemWatcher()`, `CustomDocumentOpenContext`, `CustomReadonlyEditorProvider`, `RegisterCustomEditorProviderOptions`, `Window.{registerCustomTextEditorProvider(), registerCustomReadonlyEditorProvider()}`
  • Loading branch information
tatchi authored Jan 27, 2022
1 parent fc0b573 commit 204fe99
Show file tree
Hide file tree
Showing 9 changed files with 370 additions and 20 deletions.
8 changes: 8 additions & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,14 @@

- Fix the detection of opam's root directory when no switch is detected (#831)

- Add support for opening compilation artifacts in human-readable form in the
editor (#798)

Currently supported artifacts include `.cmi`, `.cmt(i)`, `.cmo`, `.cma`,
`.cmx(a/s)`, and `.bc` files.

To learn more about these files, see: https://ocaml.org/manual/comp.html

- Warn if the extension sees not the latest OCaml-LSP version compatible with
the OCaml distribution installed in the current sandbox.

Expand Down
34 changes: 34 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
"onCommand:ocaml.show-preprocessed-document",
"onCommand:ocaml.open-pp-editor-and-ast-explorer",
"onCustomEditor:ast-editor",
"onCustomEditor:cm-files-editor",
"workspaceContains:**/dune-workspace",
"workspaceContains:**/dune",
"workspaceContains:**/dune-project",
Expand Down Expand Up @@ -946,6 +947,39 @@
"filenamePattern": "*.mli"
}
]
},
{
"viewType": "cm-files-editor",
"displayName": "OCaml Compilation Artifact Viewer",
"selector": [
{
"filenamePattern": "*.cmi"
},
{
"filenamePattern": "*.cmt"
},
{
"filenamePattern": "*.cmti"
},
{
"filenamePattern": "*.cmo"
},
{
"filenamePattern": "*.cma"
},
{
"filenamePattern": "*.cmx"
},
{
"filenamePattern": "*.cmxa"
},
{
"filenamePattern": "*.cmxs"
},
{
"filenamePattern": "*.bc"
}
]
}
]
},
Expand Down
125 changes: 116 additions & 9 deletions src-bindings/vscode/vscode.ml
Original file line number Diff line number Diff line change
Expand Up @@ -2215,6 +2215,14 @@ module TextDocumentContentProvider = struct
[@@js.builder]]
end

module FileSystemWatcher = struct
include Interface.Make ()

module OnDidChange = Event.Make (Uri)

include [%js: val onDidChange : t -> OnDidChange.t [@@js.get]]
end

module Workspace = struct
module OnDidChangeWorkspaceFolders = Event.Make (WorkspaceFolder)
module OnDidOpenTextDocument = Event.Make (TextDocument)
Expand All @@ -2235,6 +2243,15 @@ module Workspace = struct

val name : unit -> string or_undefined [@@js.get "vscode.workspace.name"]

val createFileSystemWatcher :
GlobPattern.t
-> ?ignoreCreateEvents:(bool[@js.default false])
-> ?ignoreChangeEvents:(bool[@js.default false])
-> ?ignoreDeleteEvents:(bool[@js.default false])
-> unit
-> FileSystemWatcher.t
[@@js.global "vscode.workspace.createFileSystemWatcher"]

val workspaceFile : unit -> Uri.t or_undefined
[@@js.get "vscode.workspace.workspaceFile"]

Expand Down Expand Up @@ -2310,6 +2327,26 @@ module TreeItemCollapsibleState = struct
[@@js.enum] [@@js]
end

module CustomDocument = struct
module type T = sig
include Js.T

val uri : t -> Uri.t

val dispose : t -> unit
end

include Interface.Make ()

include
[%js:
val uri : t -> Uri.t [@@js.get]

val dispose : t -> unit [@@js.call]

val create : uri:Uri.t -> dispose:(unit -> unit) -> t [@@js.builder]]
end

module TreeItemLabel = struct
include Interface.Make ()

Expand Down Expand Up @@ -2850,6 +2887,63 @@ module CustomTextEditorProvider = struct
[@@js.builder]]
end

module CustomDocumentOpenContext = struct
include Interface.Make ()

include [%js: val backupId : t -> string or_undefined [@@js.get]]
end

module CustomReadonlyEditorProvider = struct
include Interface.Generic (Ojs) ()

module Make (T : CustomDocument.T) = struct
type t = T.t generic [@@js]

include
[%js:
val openCustomDocument :
t
-> uri:Uri.t
-> openContext:CustomDocumentOpenContext.t
-> token:CancellationToken.t
-> T.t Promise.t
[@@js.call]

val resolveCustomEditor :
t
-> document:T.t
-> webviewPanel:WebviewPanel.t
-> token:CancellationToken.t
-> unit Promise.t
[@@js.call]

val create :
resolveCustomEditor:
( document:T.t
-> webviewPanel:WebviewPanel.t
-> token:CancellationToken.t
-> unit Promise.t)
-> openCustomDocument:
( uri:Uri.t
-> openContext:CustomDocumentOpenContext.t
-> token:CancellationToken.t
-> T.t Promise.t)
-> t
[@@js.builder]]
end
end

module RegisterCustomEditorProviderOptions = struct
include Interface.Make ()

include
[%js:
val supportsMultipleEditorsPerDocument : t -> bool or_undefined [@@js.get]

val create : ?supportsMultipleEditorsPerDocument:bool -> unit -> t
[@@js.builder]]
end

module Window = struct
module OnDidChangeActiveTextEditor = Event.Make (TextEditor)
module OnDidChangeVisibleTextEditors = Event.Make (Js.List (TextEditor))
Expand Down Expand Up @@ -2992,16 +3086,19 @@ module Window = struct
-> WebviewPanel.t
[@@js.global "vscode.window.createWebviewPanel"]

val registerCustomEditorProvider :
val registerCustomTextEditorProvider :
viewType:string
-> provider:
([ `CustomTextEditorProvider of CustomTextEditorProvider.t
| `CustomReadonlyEditorProvider of
CustomTextEditorProvider.t
(*TODO*)
| `CustomEditorProvider of CustomTextEditorProvider.t (*TODO*)
]
[@js.union])
-> provider:CustomTextEditorProvider.t
-> ?options:RegisterCustomEditorProviderOptions.t
-> unit
-> Disposable.t
[@@js.global "vscode.window.registerCustomEditorProvider"]

val registerCustomReadonlyEditorProvider :
viewType:string
-> provider:Ojs.t
-> ?options:RegisterCustomEditorProviderOptions.t
-> unit
-> Disposable.t
[@@js.global "vscode.window.registerCustomEditorProvider"]]

Expand Down Expand Up @@ -3061,6 +3158,16 @@ module Window = struct
let module TreeView = TreeView.Make (T) in
let options = [%js.of: TreeViewOptions.t] options in
[%js.to: TreeView.t] (createTreeView ~viewId ~options)

let registerCustomReadonlyEditorProvider (type a)
(module T : CustomDocument.T with type t = a) ~(viewType : string)
~(provider : a CustomReadonlyEditorProvider.t)
?(options : RegisterCustomEditorProviderOptions.t or_undefined) () :
Disposable.t =
let module CustomReadonlyEditorProvider =
CustomReadonlyEditorProvider.Make (T) in
let provider = [%js.of: CustomReadonlyEditorProvider.t] provider in
registerCustomReadonlyEditorProvider ~viewType ~provider ?options ()
end

module Commands = struct
Expand Down
95 changes: 89 additions & 6 deletions src-bindings/vscode/vscode.mli
Original file line number Diff line number Diff line change
Expand Up @@ -782,6 +782,20 @@ module CancellationToken : sig
-> t
end

module CustomDocument : sig
module type T = sig
include Js.T

val uri : t -> Uri.t

val dispose : t -> unit
end

include T

val create : uri:Uri.t -> dispose:(unit -> unit) -> t
end

module QuickPickItem : sig
include Js.T

Expand Down Expand Up @@ -1702,11 +1716,25 @@ module TextDocumentContentProvider : sig
-> t
end

module FileSystemWatcher : sig
include Js.T

val onDidChange : t -> Uri.t Event.t
end

module Workspace : sig
val workspaceFolders : unit -> WorkspaceFolder.t list

val name : unit -> string option

val createFileSystemWatcher :
GlobPattern.t
-> ?ignoreCreateEvents:bool
-> ?ignoreChangeEvents:bool
-> ?ignoreDeleteEvents:bool
-> unit
-> FileSystemWatcher.t

val workspaceFile : unit -> Uri.t option

val rootPath : unit -> string or_undefined
Expand Down Expand Up @@ -2168,6 +2196,55 @@ module CustomTextEditorProvider : sig
-> t
end

module CustomDocumentOpenContext : sig
include Js.T

val backupId : t -> string or_undefined
end

module CustomReadonlyEditorProvider : sig
type 'a t

module Make (T : CustomDocument.T) : sig
type nonrec t = T.t t

val openCustomDocument :
t
-> uri:Uri.t
-> openContext:CustomDocumentOpenContext.t
-> token:CancellationToken.t
-> T.t Promise.t

val resolveCustomEditor :
t
-> document:T.t
-> webviewPanel:WebviewPanel.t
-> token:CancellationToken.t
-> unit Promise.t

val create :
resolveCustomEditor:
( document:T.t
-> webviewPanel:WebviewPanel.t
-> token:CancellationToken.t
-> unit Promise.t)
-> openCustomDocument:
( uri:Uri.t
-> openContext:CustomDocumentOpenContext.t
-> token:CancellationToken.t
-> T.t Promise.t)
-> t
end
end

module RegisterCustomEditorProviderOptions : sig
include Js.T

val supportsMultipleEditorsPerDocument : t -> bool or_undefined

val create : ?supportsMultipleEditorsPerDocument:bool -> unit -> t
end

module Window : sig
val activeTextEditor : unit -> TextEditor.t option

Expand Down Expand Up @@ -2278,13 +2355,19 @@ module Window : sig
-> showOptions:ViewColumn.t
-> WebviewPanel.t

val registerCustomEditorProvider :
val registerCustomTextEditorProvider :
viewType:string
-> provider:
[ `CustomTextEditorProvider of CustomTextEditorProvider.t
| `CustomReadonlyEditorProvider of CustomTextEditorProvider.t (*TODO*)
| `CustomEditorProvider of CustomTextEditorProvider.t (*TODO*)
]
-> provider:CustomTextEditorProvider.t
-> ?options:RegisterCustomEditorProviderOptions.t
-> unit
-> Disposable.t

val registerCustomReadonlyEditorProvider :
(module CustomDocument.T with type t = 'a)
-> viewType:string
-> provider:'a CustomReadonlyEditorProvider.t
-> ?options:RegisterCustomEditorProviderOptions.t
-> unit
-> Disposable.t
end

Expand Down
9 changes: 4 additions & 5 deletions src/ast_editor.ml
Original file line number Diff line number Diff line change
Expand Up @@ -599,13 +599,12 @@ let register extension instance =
Vscode.ExtensionContext.subscribe extension ~disposable;
(*Register custom editor provider that is the AST explorer. *)
let editorProvider =
`CustomEditorProvider
(CustomTextEditorProvider.create
~resolveCustomTextEditor:(resolveCustomTextEditor instance))
CustomTextEditorProvider.create
~resolveCustomTextEditor:(resolveCustomTextEditor instance)
in
let disposable =
Vscode.Window.registerCustomEditorProvider ~viewType:"ast-editor"
~provider:editorProvider
Vscode.Window.registerCustomTextEditorProvider ~viewType:"ast-editor"
~provider:editorProvider ()
in
Vscode.ExtensionContext.subscribe extension ~disposable;
(*Register listener that monitors closing documents. *)
Expand Down
Loading

0 comments on commit 204fe99

Please sign in to comment.