[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
emacs-29 6f88de109c: ruby-mode: Support endless methods (bug#54702)
From: |
Dmitry Gutov |
Subject: |
emacs-29 6f88de109c: ruby-mode: Support endless methods (bug#54702) |
Date: |
Sun, 18 Dec 2022 07:04:53 -0500 (EST) |
branch: emacs-29
commit 6f88de109c837496003296d2b79b0d20c7c3b283
Author: Dmitry Gutov <dgutov@yandex.ru>
Commit: Dmitry Gutov <dgutov@yandex.ru>
ruby-mode: Support endless methods (bug#54702)
* lisp/progmodes/ruby-mode.el (ruby-endless-method-head-re):
New constant.
(ruby-smie-grammar): New token.
(ruby-smie--forward-token, ruby-smie--backward-token):
Recognize it.
(ruby-smie-rules): Indentation support.
(ruby-add-log-current-method): Support here too.
* test/lisp/progmodes/ruby-mode-tests.el
(ruby-add-log-current-method-after-endless-method): New test.
* test/lisp/progmodes/ruby-mode-resources/ruby.rb: New examples.
---
etc/NEWS | 3 +++
lisp/progmodes/ruby-mode.el | 28 +++++++++++++++++++--
test/lisp/progmodes/ruby-mode-resources/ruby.rb | 33 +++++++++++++++++++++++++
test/lisp/progmodes/ruby-mode-tests.el | 12 +++++++++
4 files changed, 74 insertions(+), 2 deletions(-)
diff --git a/etc/NEWS b/etc/NEWS
index 25148dc2fd..cded60cca6 100644
--- a/etc/NEWS
+++ b/etc/NEWS
@@ -2758,6 +2758,9 @@ project-dedicated or global) is specified by the new
---
*** New user option 'ruby-toggle-block-space-before-parameters'.
+---
+*** Support for endless methods.
+
** Eshell
+++
diff --git a/lisp/progmodes/ruby-mode.el b/lisp/progmodes/ruby-mode.el
index 2b1db59806..ed6044280e 100644
--- a/lisp/progmodes/ruby-mode.el
+++ b/lisp/progmodes/ruby-mode.el
@@ -134,6 +134,12 @@ This should only be called after matching against
`ruby-here-doc-beg-re'."
(defconst ruby-symbol-re (concat "[" ruby-symbol-chars "]")
"Regexp to match symbols.")
+(defconst ruby-endless-method-head-re
+ (format " *\\(self\\.\\)?%s+[?!]? *\\(([^()]*)\\)? +=" ruby-symbol-re)
+ "Regexp to match the beginning of an endless method definition.
+
+It should match the part after \"def\" and until \"=\".")
+
(defvar ruby-use-smie t)
(make-obsolete-variable 'ruby-use-smie nil "28.1")
@@ -351,7 +357,8 @@ This only affects the output of the command
`ruby-toggle-block'."
(exp (exp1) (exp "," exp) (exp "=" exp)
(id " @ " exp))
(exp1 (exp2) (exp2 "?" exp1 ":" exp1))
- (exp2 (exp3) (exp3 "." exp3))
+ (exp2 (exp3) (exp3 "." exp3)
+ (exp3 "def=" exp3))
(exp3 ("def" insts "end")
("begin" insts-rescue-insts "end")
("do" insts "end")
@@ -528,6 +535,9 @@ This only affects the output of the command
`ruby-toggle-block'."
(ruby-smie--forward-token)) ;Fully redundant.
(t ";")))
((equal tok "&.") ".")
+ ((and (equal tok "def")
+ (looking-at ruby-endless-method-head-re))
+ "def=")
(t tok)))))))))
(defun ruby-smie--backward-token ()
@@ -575,6 +585,9 @@ This only affects the output of the command
`ruby-toggle-block'."
(ruby-smie--backward-token)) ;Fully redundant.
(t ";")))
((equal tok "&.") ".")
+ ((and (equal tok "def")
+ (looking-at (concat "def" ruby-endless-method-head-re)))
+ "def=")
(t tok)))))))
(defun ruby-smie--indent-to-stmt ()
@@ -629,6 +642,11 @@ This only affects the output of the command
`ruby-toggle-block'."
(not (ruby-smie--bosp)))
(forward-char -1))
(smie-indent-virtual))
+ ((save-excursion
+ (and (smie-rule-parent-p " @ ")
+ (goto-char (nth 1 (smie-indent--parent)))
+ (smie-rule-prev-p "def=")
+ (cons 'column (- (current-column) 3)))))
(t (smie-rule-parent))))))
(`(:after . ,(or "(" "[" "{"))
;; FIXME: Shouldn't this be the default behavior of
@@ -672,6 +690,12 @@ This only affects the output of the command
`ruby-toggle-block'."
(and (smie-rule-parent-p ";" nil)
(smie-indent--hanging-p)
ruby-indent-level))
+ (`(:before . "=")
+ (save-excursion
+ (and (smie-rule-parent-p " @ ")
+ (goto-char (nth 1 (smie-indent--parent)))
+ (smie-rule-prev-p "def=")
+ (cons 'column (+ (current-column) ruby-indent-level -3)))))
(`(:after . ,(or "?" ":")) ruby-indent-level)
(`(:before . ,(guard (memq (intern-soft token) ruby-alignable-keywords)))
(when (not (ruby--at-indentation-p))
@@ -1632,7 +1656,7 @@ See `add-log-current-defun-function'."
(while (and (re-search-backward definition-re nil t)
(if (if (string-equal "def" (match-string 1))
;; We're inside a method.
- (if (ruby-block-contains-point start)
+ (if (ruby-block-contains-point (1-
start))
t
;; Try to match a method only once.
(setq definition-re module-re)
diff --git a/test/lisp/progmodes/ruby-mode-resources/ruby.rb
b/test/lisp/progmodes/ruby-mode-resources/ruby.rb
index 43f8bebcfc..5636a4fc0e 100644
--- a/test/lisp/progmodes/ruby-mode-resources/ruby.rb
+++ b/test/lisp/progmodes/ruby-mode-resources/ruby.rb
@@ -177,6 +177,9 @@ qux :+,
zzz @abc,
4
+foo a = 5,
+ b
+
b = $:
c = ??
@@ -503,3 +506,33 @@ def resolve(**args)
member.call(**args)
end
+
+# Endless methods.
+class Bar
+ def foo(abc) = bar +
+ baz
+
+ def self.bar =
+ 123 +
+ 4
+
+ def foo(...) = z
+
+ def request_params = {
+ headers: request_headers,
+ body: request_body
+ }
+
+ def self.foo(
+ baz,
+ bar
+ ) =
+ what
+
+ def foo=(
+ baz,
+ bar
+ )
+ hello
+ end
+end
diff --git a/test/lisp/progmodes/ruby-mode-tests.el
b/test/lisp/progmodes/ruby-mode-tests.el
index e90a9e4075..9be01dc78f 100644
--- a/test/lisp/progmodes/ruby-mode-tests.el
+++ b/test/lisp/progmodes/ruby-mode-tests.el
@@ -605,6 +605,18 @@ VALUES-PLIST is a list with alternating index and value
elements."
(search-backward "FOO")
(should (string= (ruby-add-log-current-method) "M::C"))))
+(ert-deftest ruby-add-log-current-method-after-endless-method ()
+ (ruby-with-temp-buffer (ruby-test-string
+ "module M
+ | class C
+ | def foo =
+ | 4_
+ | end
+ |end")
+ (search-backward "_")
+ (delete-char 1)
+ (should (string= (ruby-add-log-current-method) "M::C#foo"))))
+
(defvar ruby-block-test-example
(ruby-test-string
"class C
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- emacs-29 6f88de109c: ruby-mode: Support endless methods (bug#54702),
Dmitry Gutov <=