Add new keywords of Python 3.5
Python 3.5, released in mid September 2015, introduced a few new keywords to better support asynchronous code, "async" and "await" in particular. See https://www.python.org/dev/peps/pep-0492/ for details. (Bug#21783) * lisp/progmodes/python.el (python-rx-constituents): Add async def/for/with as block-start and async def as defun. * lisp/progmodes/python.el (python-font-lock-keywords): Add async def/for/with as keyword. * test/automated/python-tests.el (python-indent-after-async-block-1, python-indent-after-async-block-2, python-indent-after-async-block-3, python-nav-beginning-of-defun-3): New tests to test indentation and navigation for the async keyword.
This commit is contained in:
parent
ccb75d72bd
commit
fa7886a46f
2 changed files with 67 additions and 2 deletions
|
@ -372,7 +372,10 @@
|
||||||
(defconst python-rx-constituents
|
(defconst python-rx-constituents
|
||||||
`((block-start . ,(rx symbol-start
|
`((block-start . ,(rx symbol-start
|
||||||
(or "def" "class" "if" "elif" "else" "try"
|
(or "def" "class" "if" "elif" "else" "try"
|
||||||
"except" "finally" "for" "while" "with")
|
"except" "finally" "for" "while" "with"
|
||||||
|
;; Python 3.5+ PEP492
|
||||||
|
(and "async" (+ space)
|
||||||
|
(or "def" "for" "with")))
|
||||||
symbol-end))
|
symbol-end))
|
||||||
(dedenter . ,(rx symbol-start
|
(dedenter . ,(rx symbol-start
|
||||||
(or "elif" "else" "except" "finally")
|
(or "elif" "else" "except" "finally")
|
||||||
|
@ -383,7 +386,11 @@
|
||||||
symbol-end))
|
symbol-end))
|
||||||
(decorator . ,(rx line-start (* space) ?@ (any letter ?_)
|
(decorator . ,(rx line-start (* space) ?@ (any letter ?_)
|
||||||
(* (any word ?_))))
|
(* (any word ?_))))
|
||||||
(defun . ,(rx symbol-start (or "def" "class") symbol-end))
|
(defun . ,(rx symbol-start
|
||||||
|
(or "def" "class"
|
||||||
|
;; Python 3.5+ PEP492
|
||||||
|
(and "async" (+ space) "def"))
|
||||||
|
symbol-end))
|
||||||
(if-name-main . ,(rx line-start "if" (+ space) "__name__"
|
(if-name-main . ,(rx line-start "if" (+ space) "__name__"
|
||||||
(+ space) "==" (+ space)
|
(+ space) "==" (+ space)
|
||||||
(any ?' ?\") "__main__" (any ?' ?\")
|
(any ?' ?\") "__main__" (any ?' ?\")
|
||||||
|
@ -515,6 +522,8 @@ The type returned can be `comment', `string' or `paren'."
|
||||||
;; fontified like that in order to keep font-lock consistent between
|
;; fontified like that in order to keep font-lock consistent between
|
||||||
;; Python versions.
|
;; Python versions.
|
||||||
"nonlocal"
|
"nonlocal"
|
||||||
|
;; Python 3.5+ PEP492
|
||||||
|
(and "async" (+ space) (or "def" "for" "with"))
|
||||||
;; Extra:
|
;; Extra:
|
||||||
"self")
|
"self")
|
||||||
symbol-end)
|
symbol-end)
|
||||||
|
|
|
@ -614,6 +614,42 @@ something
|
||||||
(should (eq (car (python-indent-context)) :after-line))
|
(should (eq (car (python-indent-context)) :after-line))
|
||||||
(should (= (python-indent-calculate-indentation) 0))))
|
(should (= (python-indent-calculate-indentation) 0))))
|
||||||
|
|
||||||
|
(ert-deftest python-indent-after-async-block-1 ()
|
||||||
|
"Test PEP492 async def."
|
||||||
|
(python-tests-with-temp-buffer
|
||||||
|
"
|
||||||
|
async def foo(a, b, c=True):
|
||||||
|
"
|
||||||
|
(should (eq (car (python-indent-context)) :no-indent))
|
||||||
|
(should (= (python-indent-calculate-indentation) 0))
|
||||||
|
(goto-char (point-max))
|
||||||
|
(should (eq (car (python-indent-context)) :after-block-start))
|
||||||
|
(should (= (python-indent-calculate-indentation) 4))))
|
||||||
|
|
||||||
|
(ert-deftest python-indent-after-async-block-2 ()
|
||||||
|
"Test PEP492 async with."
|
||||||
|
(python-tests-with-temp-buffer
|
||||||
|
"
|
||||||
|
async with foo(a) as mgr:
|
||||||
|
"
|
||||||
|
(should (eq (car (python-indent-context)) :no-indent))
|
||||||
|
(should (= (python-indent-calculate-indentation) 0))
|
||||||
|
(goto-char (point-max))
|
||||||
|
(should (eq (car (python-indent-context)) :after-block-start))
|
||||||
|
(should (= (python-indent-calculate-indentation) 4))))
|
||||||
|
|
||||||
|
(ert-deftest python-indent-after-async-block-3 ()
|
||||||
|
"Test PEP492 async for."
|
||||||
|
(python-tests-with-temp-buffer
|
||||||
|
"
|
||||||
|
async for a in sequencer():
|
||||||
|
"
|
||||||
|
(should (eq (car (python-indent-context)) :no-indent))
|
||||||
|
(should (= (python-indent-calculate-indentation) 0))
|
||||||
|
(goto-char (point-max))
|
||||||
|
(should (eq (car (python-indent-context)) :after-block-start))
|
||||||
|
(should (= (python-indent-calculate-indentation) 4))))
|
||||||
|
|
||||||
(ert-deftest python-indent-after-backslash-1 ()
|
(ert-deftest python-indent-after-backslash-1 ()
|
||||||
"The most common case."
|
"The most common case."
|
||||||
(python-tests-with-temp-buffer
|
(python-tests-with-temp-buffer
|
||||||
|
@ -1493,6 +1529,26 @@ class C(object):
|
||||||
(beginning-of-line)
|
(beginning-of-line)
|
||||||
(point))))))
|
(point))))))
|
||||||
|
|
||||||
|
(ert-deftest python-nav-beginning-of-defun-3 ()
|
||||||
|
(python-tests-with-temp-buffer
|
||||||
|
"
|
||||||
|
class C(object):
|
||||||
|
|
||||||
|
async def m(self):
|
||||||
|
return await self.c()
|
||||||
|
|
||||||
|
async def c(self):
|
||||||
|
pass
|
||||||
|
"
|
||||||
|
(python-tests-look-at "self.c()")
|
||||||
|
(should (= (save-excursion
|
||||||
|
(python-nav-beginning-of-defun)
|
||||||
|
(point))
|
||||||
|
(save-excursion
|
||||||
|
(python-tests-look-at "async def m" -1)
|
||||||
|
(beginning-of-line)
|
||||||
|
(point))))))
|
||||||
|
|
||||||
(ert-deftest python-nav-end-of-defun-1 ()
|
(ert-deftest python-nav-end-of-defun-1 ()
|
||||||
(python-tests-with-temp-buffer
|
(python-tests-with-temp-buffer
|
||||||
"
|
"
|
||||||
|
|
Loading…
Add table
Reference in a new issue