branch: elpa/evil-matchit commit dead63c7d04c693abdbf1c2e23e8f1771699a64d Author: Chen Bin <chenbin...@gmail.com> Commit: Chen Bin <chenbin...@gmail.com>
add unit test --- .gitignore | 2 + .travis.yml | 16 ++++++ Makefile | 17 ++++++ README.org | 2 +- evil-matchit-html.el | 33 +++++++---- evil-matchit-sdk.el | 3 +- evil-matchit.el | 7 ++- tests/evil-matchit-tests.el | 132 ++++++++++++++++++++++++++++++++++++++++++++ 8 files changed, 198 insertions(+), 14 deletions(-) diff --git a/.gitignore b/.gitignore index 5ea5a9ea3e..566d7ca5bd 100644 --- a/.gitignore +++ b/.gitignore @@ -25,3 +25,5 @@ Session.vim *.tar *.elc +deps/ +TAGS diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000000..76135791e7 --- /dev/null +++ b/.travis.yml @@ -0,0 +1,16 @@ +language: nix + +os: + - linux + +env: + - EMACS_CI=emacs-24-4 + - EMACS_CI=emacs-25-3 + - EMACS_CI=emacs-26-3 + - EMACS_CI=emacs-snapshot + +install: + - bash <(curl https://raw.githubusercontent.com/purcell/nix-emacs-ci/master/travis-install) + +script: + - bash <(make test) diff --git a/Makefile b/Makefile new file mode 100644 index 0000000000..a6ed2b7173 --- /dev/null +++ b/Makefile @@ -0,0 +1,17 @@ +# -*- Makefile -*- +SHELL = /bin/sh +EMACS ?= emacs + +clean: + @rm -f *~ + @rm -f \#*\# + @rm -f *.elc + +.PHONY: deps +deps: + @mkdir -p deps; + @if [ ! -f deps/evil-1.14.0/evil.el ]; then curl -L https://stable.melpa.org/packages/evil-1.14.0.tar | tar x -C deps/; fi; + +.PHONY: test +test: deps clean + @$(EMACS) -batch -Q -L . -L deps/evil-1.14.0 -l evil-matchit.el -l tests/evil-matchit-tests.el \ No newline at end of file diff --git a/README.org b/README.org index 0f3766f0a8..b66d0b4d5c 100644 --- a/README.org +++ b/README.org @@ -1,5 +1,5 @@ * evil-matchit - +[[https://travis-ci.org/redguardtoo/evil-matchit][https://travis-ci.org/redguardtoo/evil-matchit.svg?branch=master]] [[http://melpa.org/#/evil-matchit][file:http://melpa.org/packages/evil-matchit-badge.svg]] [[http://stable.melpa.org/#/evil-matchit][file:http://stable.melpa.org/packages/evil-matchit-badge.svg]] Vim [[http://www.vim.org/scripts/script.php?script_id=39][matchit.vim]] by Benji Fisher is ported into Emacs. diff --git a/evil-matchit-html.el b/evil-matchit-html.el index c4dd715dbd..305bebe913 100644 --- a/evil-matchit-html.el +++ b/evil-matchit-html.el @@ -40,8 +40,11 @@ It starts from POSITION and possibly ends at line end." (car (split-string partial-line "[ \t]+")))) (defun evilmi-html--detect-self-closing-tag-end (char position) - "Use CHAR at POSITION to test if it's the end of self closing tag. -If at the end of self closing tag, " + "Use CHAR at POSITION to test if it's the end of self closing tag." + (when evilmi-debug + (message "evilmi-html--detect-self-closing-tag-end called => %s %s" + char + position)) (when (or (and (eq char ?>) (eq (evilmi-sdk-get-char (1- position)) ?/)) (and (eq char ?/) @@ -49,11 +52,14 @@ If at the end of self closing tag, " (list (if (eq char ?>) position (1+ position)) 1 ""))) (defun evilmi-html--detect-normal-tags (char position) - "Test one of matched tags or beginning of self closing tag." + "Test matched tags or beginning of self closing tag. +Use CHAR at POSITION." (let* ((begin (line-beginning-position)) (end (line-end-position)) (looping t) (found_tag -1)) + (when evilmi-debug + (message "evilmi-html--detect-normal-tags: position=%s" position)) (save-excursion ;; search backward for "<" (unless (eq char ?<) @@ -67,10 +73,12 @@ If at the end of self closing tag, " ;; search forward for "<" (unless (eq char ?<) (save-excursion - (while (and (>= end (point)) (not (eq char ?<))) + (while (and (>= end (point)) + (not (eq char ?<)) + (< (point) (point-max))) (setq char (following-char)) (setq position (point)) - (forward-char)))) + (unless (eq (point) (point-max)) (forward-char))))) ;; a valid html tag should be like <[^;] (unless (and (eq char ?<) @@ -115,10 +123,14 @@ If at the end of self closing tag, " (defun evilmi-html-get-tag () "Get current tag." (let* ((char (following-char)) - (position (point))) - (if evilmi-debug (message "evilmi-html-get-tag called. position" position)) - (or (evilmi-html--detect-self-closing-tag-end char position) - (evilmi-html--detect-normal-tags char position)))) + (position (point)) + rlt) + (if evilmi-debug (message "evilmi-html-get-tag called. position=%s" position)) + (setq rlt (or (evilmi-html--detect-self-closing-tag-end char position) + (evilmi-html--detect-normal-tags char position))) + ;; restore original position + (goto-char position) + rlt)) ;;;###autoload (defun evilmi-html-jump (info num) @@ -127,7 +139,8 @@ If at the end of self closing tag, " ;; `web-mode-forward-sexp' is assigned to `forward-sexp-function' ;; it's buggy in web-mode v11, here is the workaround (forward-sexp-function nil)) - (if evilmi-debug (message "evilmi-html-jump called. tag-type=%s" tag-type)) + (when evilmi-debug + (message "evilmi-html-jump called. tag-type=%s info=%s" tag-type info)) (cond ((eq 1 tag-type) (sgml-skip-tag-backward num)) diff --git a/evil-matchit-sdk.el b/evil-matchit-sdk.el index 0f22e387a2..14a31fa414 100644 --- a/evil-matchit-sdk.el +++ b/evil-matchit-sdk.el @@ -39,8 +39,7 @@ If font-face-under-cursor is NOT nil, the quoted string is being processed." (setq rlt (eq (setq ff (get-text-property p 'face)) (get-text-property (+ 1 p) 'face))))) - (when evilmi-debug - (message "evilmi-sdk-jump-forward-p => (%s %s %s)" rlt ff (string ch))) + (if evilmi-debug (message "evilmi-sdk-jump-forward-p => (%s %s %s)" rlt ff (string ch))) (list rlt ff ch))) (defun evilmi-sdk-simple-jump () diff --git a/evil-matchit.el b/evil-matchit.el index 6d2e9ef0c3..86e58d5316 100644 --- a/evil-matchit.el +++ b/evil-matchit.el @@ -214,7 +214,12 @@ If IS-FORWARD is t, jump forward; or else jump backward." ;; jump only once if the jump is successful (setq jumped t)) (when evilmi-debug - (message "rlt=%s rule=%s p=%s jumped=%s" rlt rule (point) jumped)))) + (message "rlt=%s rule=%s p=%s jumped=%s idea-dest=%s" + rlt + rule + (point) + jumped + ideal-dest)))) ;; give `evilmi-sdk-simple-jump' a second chance (unless jumped diff --git a/tests/evil-matchit-tests.el b/tests/evil-matchit-tests.el new file mode 100644 index 0000000000..f7d9a9a01a --- /dev/null +++ b/tests/evil-matchit-tests.el @@ -0,0 +1,132 @@ +;;; evil-matchit-tests.el --- unit tests for evil-matchit -*- coding: utf-8 -*- + +;; Author: Chen Bin <chenbin DOT sh AT gmail DOT com> + +;;; License: + +;; This file is not part of GNU Emacs. + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation; either version 3, or (at your option) +;; any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program; if not, write to the Free Software +;; Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +;;; Commentary: + +(require 'ert) +(require 'evil-matchit) + +(setq evilmi-may-jump-by-percentage nil) +(setq evilmi-debug nil) ; debug + +(ert-deftest evilmi-test-generic () + (let* ((str "123456") + (jump-offset (+ 1 (length str)))) + (with-temp-buffer + (insert (format "[%s]" str)) + (insert (format "{([%s])}" str)) + (insert "=BEG=\n{\nhello world\n}\n=END=") + ;; test first segment + (goto-char (point-min)) + (evilmi-jump-items) + (should (eq (point) (+ (point-min) jump-offset))) + ;; jump back + (evilmi-jump-items) + (should (eq (point) (point-min))) + + ;; test "{}" + (goto-char (+ (point-min) 1 jump-offset)) + (evilmi-jump-items) + (should (eq (following-char) ?})) + (evilmi-jump-items) + (should (eq (following-char) ?{)) + + ;; test "()" + (goto-char (+ (point-min) 2 jump-offset)) + (evilmi-jump-items) + (should (eq (following-char) 41)) ; ?) + (evilmi-jump-items) + (should (eq (following-char) 40)) ; ?( + + ;; test deleting {} + (goto-char (point-min)) + (search-forward "=BEG=") + (forward-char) + (let* ((pos (- (point) (length "=BEG=") 1))) + (should (eq (following-char) ?{)) + (evilmi-delete-items) + (should (string= (buffer-substring pos (point-max)) "=BEG=\n\n=END="))) + + (should (eq major-mode 'fundamental-mode))))) + +(ert-deftest evilmi-test-javascript () + (let* ((str "function hello() {\n console.log('hello world');\n}")) + (with-temp-buffer + (insert str) + (js-mode) + ;; for javascript, jump from anywhere in function beginning + (goto-char (+ 3 (point-min))) + (evilmi-jump-items) + (should (eq (following-char) ?})) + + ;; jump from start again + (goto-char (point-min)) + (search-forward "{") + (evilmi-jump-items) + (should (eq (following-char) ?})) + ;; jump back + (evilmi-jump-items) + (should (eq (following-char) ?{)) + + ;; jump between ends of string can't be tested. + ;; because font face is not useable in batch mode + + (should (eq major-mode 'js-mode))))) + +(ert-deftest evilmi-test-html () + (let* ((str "<html lang=\"en\">\n<head>\n<link rel=\"icon\" href=\"%PUBLIC_URL%/favicon.ico\" />\n</head>\n<body>\n<p>Hello world!</p>\n</body>\n</html>")) + (with-temp-buffer + (insert str) + (html-mode) + + ;; jump from start again + (goto-char (point-min)) + (search-forward "<head") + ;; Please note it jumps to line feed + (evilmi-jump-items) + (goto-char (1- (point))) + (should (eq (following-char) ?>)) + (should (string= (thing-at-point 'symbol) "/head")) + + ;; self closing tag + (goto-char (point-min)) + (search-forward "<link") + (evilmi-jump-items) + (goto-char (1- (point))) + (should (eq (following-char) ?>)) + (should (string= (thing-at-point 'symbol) "/")) + (evilmi-jump-items) + (should (eq (following-char) ?<)) + (forward-char) + (should (string= (thing-at-point 'word) "link")) + + ;; tags in one line + (goto-char (point-min)) + (search-forward "<p") + (evilmi-jump-items) + (goto-char (1- (point))) + (should (eq (following-char) ?>)) + (should (string= (thing-at-point 'symbol) "/p")) + + (should (eq major-mode 'html-mode))))) +(ert-run-tests-batch-and-exit) +;;; evil-matchit-tests.el ends here