Skip to content

Commit be08deb

Browse files
hut8biern
authored andcommitted
Update of prelude-go to replace gocode backend with lsp-mode and gopls (bbatsov#1363)
1 parent eed1073 commit be08deb

File tree

3 files changed

+104
-12
lines changed

3 files changed

+104
-12
lines changed

.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -30,3 +30,4 @@ transient/
3030
var/
3131
.cache/
3232
.lsp-session*
33+
gotools/

doc/modules/go.md

+87
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
# Prelude Go
2+
3+
This module builds on top of the shared [Programming](programming.md)
4+
module, as well as the [Prelude-LSP](lsp.md) module.
5+
6+
The following keybindings are set by default, which are not present in
7+
each mode's default bindings:
8+
9+
* <kbd>C-c a</kbd> (`go-test-current-project`)
10+
* <kbd>C-c m</kbd> (`go-test-current-file`)
11+
* <kbd>C-c .</kbd> (`go-test-current-test`)
12+
* <kbd>C-c b</kbd> (`go-run`)
13+
* <kbd>C-h f</kbd> (`godoc-at-point`)
14+
15+
Run <kbd>C-h m</kbd> for all the key bindings and other documentation.
16+
17+
There are two ways to manage projects in Go: `$GOPATH` and with Go
18+
modules. Modules are the newer, recommended method. Read [Using Go
19+
Modules](https://go.dev/blog/using-go-modules) to learn about this, if
20+
you are unfamiliar with the subject. Many of the tools used by Prelude
21+
Go may provide functions that are broken with modules. There is
22+
usually another function that will work properly; when in doubt, use a
23+
function provided by `lsp-mode` which is documented below.
24+
25+
Generics were added to Go in 1.18. `gopls`, the backend for `lsp-mode`
26+
setup herein, supports generics as long as `gopls` itself was built
27+
with 1.18+. Other minor modes may not support generics yet.
28+
29+
## Go Mode
30+
31+
`prelude-go` builds on several useful Go tools, and establishes sensible
32+
defaults. The major mode is `go-mode`. Documentation is available at [github.com/dominikh/go-mode.el](https://github.com/dominikh/go-mode.el)
33+
34+
## Go Projectile
35+
36+
[Projectile](https://github.com/bbatsov/projectile) integration is
37+
provided by [go-projectile](https://github.com/dougm/go-projectile).
38+
39+
This provides:
40+
41+
* Projectile integration
42+
* Switching GOPATH if desired per project (customizable via
43+
`customize`)
44+
* Ability to download all commonly used `go` tools via <kbd>M-x
45+
go-projectile-install-tools</kbd> and update them via <kbd>M-x
46+
go-projectile-update-tools</kbd>
47+
* Very basic refactoring via `go-projectile-rewrite` (uses `gofmt -r`)
48+
* Support for `go get` and `go get -u` via `go-projectile-get` and
49+
`go-projectile-update`.
50+
51+
See its documentation for details.
52+
53+
## LSP Mode and LSP UI
54+
55+
[LSP](https://microsoft.github.io/language-server-protocol/) (Language
56+
Server Protocol) is a protocol that allows editors to use an external
57+
"language server" to provide features like autocompletion,
58+
documentation, and code navigation rather than implementing these
59+
features separately in each editor. Emacs supports LSP via
60+
`lsp-mode`. The language server used is
61+
[gopls](https://github.com/golang/tools/tree/master/gopls).
62+
63+
To install `gopls`, change to a directory outside of `$GOPATH` or any
64+
module (e.g., `/tmp`) and execute:
65+
66+
```
67+
go install golang.org/x/tools/gopls@latest
68+
```
69+
70+
Ensure that `gopls` is in your `$PATH`.
71+
72+
Excellent documentation for `lsp-mode` and `lsp-ui` are provided at [emacs-lsp.github.io/lsp-mode/](https://emacs-lsp.github.io/lsp-mode/)
73+
74+
If a feature, such as documentation, refactoring, indenting, etc. is
75+
provided by `lsp`, you should use it instead of calling to another
76+
tool. `gopls` is the officially maintained tool that supercedes
77+
functionality in other tools, like `gocode`, and works properly with
78+
modules and generics.
79+
80+
Company support is automatically added that works with `lsp`.
81+
82+
## GoTest
83+
84+
[gotest](https://github.com/nlamirault/gotest.el) is also provided
85+
while editing Go files in order to run tests more easily. The bindings
86+
provided by `prelude-go` are listed at the top because `gotest` does
87+
not set any.

modules/prelude-go.el

+16-12
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,13 @@
2929
;;; Code:
3030

3131
(require 'prelude-programming)
32+
(require 'prelude-lsp)
3233

3334
(prelude-require-packages '(go-mode
34-
company-go
35-
go-eldoc
3635
go-projectile
36+
lsp-mode
37+
lsp-ui
38+
company
3739
gotest))
3840

3941
(require 'go-projectile)
@@ -58,23 +60,25 @@
5860
(when goimports
5961
(setq gofmt-command goimports)))
6062

61-
;; gofmt on save
62-
(add-hook 'before-save-hook 'gofmt-before-save nil t)
63-
6463
;; stop whitespace being highlighted
6564
(whitespace-toggle-options '(tabs))
6665

67-
;; Company mode settings
68-
(set (make-local-variable 'company-backends) '(company-go))
69-
70-
;; El-doc for Go
71-
(go-eldoc-setup)
72-
7366
;; CamelCase aware editing operations
7467
(subword-mode +1))
7568

76-
(setq prelude-go-mode-hook 'prelude-go-mode-defaults)
69+
;; if yas is present, this enables yas-global-mode
70+
;; which provides completion via company
71+
(if (fboundp 'yas-global-mode)
72+
(yas-global-mode))
73+
74+
;; configure lsp for go
75+
(defun lsp-go-install-save-hooks ()
76+
(add-hook 'before-save-hook #'lsp-format-buffer t t)
77+
(add-hook 'before-save-hook #'lsp-organize-imports t t))
78+
(add-hook 'go-mode-hook #'lsp-go-install-save-hooks)
79+
(add-hook 'go-mode-hook #'lsp-deferred)
7780

81+
(setq prelude-go-mode-hook 'prelude-go-mode-defaults)
7882
(add-hook 'go-mode-hook (lambda ()
7983
(run-hooks 'prelude-go-mode-hook))))
8084

0 commit comments

Comments
 (0)