cort.el
is lightweight Emacs Lisp unit test package.
(ert.el
is attached as standard to Emacs,
it is difficult to understand the displayed error.)
- Put
cort.el
your package root folder. - Create
Makefile
,.travis.yml
if you need. - Create test cases definition file as
[package-name]-tests.el
.
(Please look at the file of this repository for a practical example.)
Makefile
sample is shown below.
TOP := $(dir $(lastword $(MAKEFILE_LIST)))
EMACS ?= emacs
LOAD_PATH := -L $(TOP)
BATCH := $(EMACS) -Q --batch $(LOAD_PATH)
ELS := cort.el # compiling .el list
ELCS := $(ELS:.el=.elc)
all: build
build: $(ELCS)
%.elc: %.el
@printf "Compiling $<\n"
@$(BATCH) -f batch-byte-compile $<
check: build
# If byte compile for specific emacs,
# set EMACS such as `EMACS=26.1 make check`.
$(BATCH) -l corts.el -f cort-tests-run
clean:
-find . -type f -name "*.elc" | xargs rm
.travis.yml
sumple is shown below.
language: generic
sudo: false
env:
global:
- CURL="curl -fsSkL --retry 9 --retry-delay 9"
matrix:
- EMACS_VERSION=23.4
- EMACS_VERSION=24.5
- EMACS_VERSION=25.3
- EMACS_VERSION=26.1
- EMACS_VERSION=master
install:
- $CURL -O https://github.com/npostavs/emacs-travis/releases/download/bins/emacs-bin-${EMACS_VERSION}.tar.gz
- tar xf emacs-bin-${EMACS_VERSION}.tar.gz -C /
- export EMACS=/tmp/emacs/bin/emacs
script:
- make
- make check
cort.el
sumple is shown below.
;; require depends package
(require 'cort)
;; if you need temporary functions for a test, define this.
(defun quote-a ()
'a)
;; define test cases.
(cort-deftest simple
'((:equal var
'a)
(:= 100
100)))
(cort-deftest quote-a
'((:eq 'a 'a)
(:eq (quote-a) 'a)
(:eq 'a (quote-a))
(:eq (quote-a) (quote-a))))
(cort-deftest arith
'((:= (+ 4 5) 9)
(:= (- 4 5) -1)
(:= (* 4 5) 20)
(:= (/ 4 5) 0)
(:= (/ 4.0 5) 0.8)
(:= (mod 4 5) 4)))
(cort-deftest string-concat
'((:string= (concat "aaa" "bbb") "aaabbb")
(:string= (mapconcat #'identity '("aaa" "bbb" "ccc") ",")
"aaa,bbb,ccc")))
(cort-deftest string-split
'((:equal (split-string "aaa,bbb,ccc" ",") '("aaa" "bbb" "ccc"))))
(cort-deftest string-length
'((:= (length "asdfg") 5)
(:= (length "あいうえお") 5)
(:= (string-width "あいうえお") 10)))
(cort-deftest string-pickup
'((:string= (substring "abcdef" 0 2) "ab")
(:string= (substring "abcdef" 0 -2) "abcd")
(:string= (substring "abcdef" 0 -1) "abcde")
(:string= (substring "abcdef" 2) "cdef")))
(cort-deftest string-serch
'((:= (string-match "bc" "abcd") 1)))
(cort-deftest err
'((:cort-error 'void-function (a 'a))
(:cort-error 'error (a 'a))
(:cort-error 'arith-error (/ 1 0))
(:cort-error 'void-variable (+ 1 a))))
cort-deftest
will receive test-name
and test-configuration-list
,
and add-to-list
to cort-cases
defined at inside of cort.el
.
Therefore, define same test case by cort-deftest
, not running test twice.
Dupulicated test-name
is allowed.
test-configuration
accept list of the form (:KEY GIVEN EXPECT)
,
expect to return t
when eval (KEY GIVEN EXPECT)
.
By defining like this, any comparison function can use that returns a boolean value
such as eq
, equal
, or =
.
This flexible test notation is one of the important merits of cort.el
.
If you pass a list of the form (:cort-error 'ERROR-TYPE FORM)
to cort-deftest
,
'ERROR-TYPE
accepts symbol such as error symbol and
expects 'ERROR-TYPE
error to occur when evaluating (FORM)
.
When writing many test cases, it is troublesome to write common parts many times.
Therefore, you can let the macro make the test case as shown below.
(cort-deftest leaf-test/:if-1
(:equal
(macroexpand-1 '(leaf foo :if t))
'(if t
(progn
(require (quote foo) nil nil)))))
(cort-deftest leaf-test/:if-2
(:equal
(macroexpand-1 '(leaf foo :if (and t t)))
'(if (and t t)
(progn
(require (quote foo) nil nil)))))
(cort-deftest leaf-test/:if-3
(:equal
(macroexpand-1 '(leaf foo :if nil))
'(if nil
(progn
(require (quote foo) nil nil)))))
;; ...
;; Almost test case is (cort-deftest NAME (:equal (macroexpand 'FORM) 'EXPECT))
;; -> Create macro to (FORM 'EXPECT) convert to (:equal (macroexpand 'FORM) 'EXPECT)
;; test target macro
(defmacro package-require (package)
`(require ,package))
;; Macro to expand FORM and compare it with EXPECT for equal test case
(defmacro match-expansion (form expect)
`(:equal (macroexpand ',form) ,expect))
(cort-deftest match-expansion0
(match-expansion
(package-require 'use-package)
'(require 'use-package)))
(cort-deftest match-expansion1
(:equal (macroexpand '(package-require 'use-package))
'(require 'use-package)))
match-expansion0
and match-expansion1
are equivalent since macros are expanded.
(You can also use a function that returns a list to be accepted by cort-deftest
see cort.el.
However, test definitions and test runs should usually be separated, and you should not run all forms to immediate when you define a test.
Therefore, we usually recommend using macros.)
- Add
cort-test
prefix to all functions macros and change below function names. - Remove environment keyword such as
:cort-if
,:cort-emacs<
,,,Use normal condition functions in test definition.
- A now expects a list of forms as the second argument.
With this change, short and easy to understand test definition is now possible.
cort
has renamed tocort-test
MELPA ignore
*-test.el
and*-tests.el
by default. With renamecort.el
tocort-test.el
, MELPA can ignore this test framework by default.However, since this prefix has not changed, this effect is minimal.
srt
has renamed tocort
All
srt
suffix flag is renamed tocort
suffix.
- :error flag has changed to :srt-error
:error
flag has changed to:srt-error
so please fix testcase.;; srt v1.0 notation (srt-deftest err:1 (:error 'void-function (a 'a))) ;; srt v2.0 notation (srt-deftest err:1 (:srt-error 'void-function (a 'a)))
Bundling Emacs-22.1 on macOS 10.13 (High Sierra), we support this.
I love OSS and I am dreaming of working on it as full-time job.
With your support, I will be able to spend more time at OSS!
All feedback and suggestions are welcome!
You can use github issues, but you can also use Slack if you want a more casual conversation.
travis CI test cort-test.el
with oll Emacs version 22 or above.
I think that it is difficult to prepare the environment locally, so I think that it is good to throw PR and test travis for the time being!
Feel free to send PR!
Affero General Public License Version 3 (AGPLv3) Copyright (c) Naoya Yamashita - https://conao3.com https://github.com/conao3/cort-test.el/blob/master/LICENSE
- Naoya Yamashita (conao3)
- Kazuya Sugiyama (Kzflute)
Advice and comments given by Emacs-JP’s forum member has been a great help
in developing cort-test.el
.
Thank you very much!!