You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
This repo is archived. You can view files and clone it, but cannot push or open issues/pull-requests.

125 lines
4.7 KiB
Scheme

;;; Copyright (c) 2000-2018 Andrew W. Keep, R. Kent Dybvig
;;; See the accompanying file Copyright for details
(library (tests unit-test-helpers)
(export test-suite test assert-equal? assert-error with-output-to-string format-error-message)
(import (rnrs) (tests unit-test-helpers-implementation) (only (nanopass helpers) errorf))
(define-syntax test-suite
(lambda (x)
(define name->run-name
(lambda (name)
(datum->syntax name
(string->symbol
(string-append "run-" (symbol->string (syntax->datum name)))))))
(syntax-case x ()
[(_ name test test* ...)
(with-syntax ([run (name->run-name #'name)])
#'(define run
(lambda ()
(display "Running ")
(write (quote name))
(display " test suite...\n")
(let f ([tests (list (lambda () test) (lambda () test*) ...)]
[successes 0] [failures 0] [exceptions 0])
(if (null? tests)
(begin
(display "Ran ")
(write (+ successes failures exceptions))
(display " tests with ")
(write successes)
(display " successes, ")
(write failures)
(display " failures, and ")
(write exceptions)
(display " exceptions\n")
(and (= failures 0) (= exceptions 0)))
(guard (e [else
(display " caught expection... ")
(display-condition e)
(newline)
(f (cdr tests) successes failures
(+ exceptions 1))])
(let ([result ((car tests))])
(write result)
(newline)
(if result
(f (cdr tests) (+ successes 1) failures
exceptions)
(f (cdr tests) successes (+ failures 1)
exceptions)))))))))])))
(define-syntax test
(syntax-rules ()
[(_ name assertion assertion* ...)
(begin
(display " Testing ")
(write (quote name))
(display " ...")
(and assertion assertion* ...))]))
;; extended to cover record equality, but not doing the union-find
;; equality we should be doing.
(define stupid-extended-equal?
(lambda (x y)
(or (equal? x y)
(and (record? x)
(record? y)
(record=? x y)))))
(define record-type-accessors
(lambda (rtd)
(let loop ([i (vector-length (record-type-field-names rtd))] [ls '()])
(if (fx=? i 0)
ls
(let ([i (fx- i 1)])
(loop i (cons (record-accessor rtd i) ls)))))))
(define record=?
(lambda (x y)
(let ([rtd (record-rtd x)])
(and (eq? rtd (record-rtd y))
(let loop ([rtd rtd])
(or (eq? rtd #f)
(and (for-all (lambda (ac) (stupid-extended-equal? (ac x) (ac y))) (record-type-accessors rtd))
(loop (record-type-parent rtd)))))))))
(define-syntax assert-equal?
(syntax-rules ()
[(_ expected actual)
(or (stupid-extended-equal? expected actual)
(begin
(newline)
(display "!!! ")
(write actual)
(display " does not match expected: ")
(write expected)
(newline)
#f))]))
(define-syntax assert-error
(syntax-rules ()
[(_ ?msg ?expr)
(let ([msg ?msg])
(guard (e [else
(let ([e-msg (with-output-to-string
(lambda ()
(display-condition e)))])
(or (string=? msg e-msg)
(begin
(newline)
(display "!!! expected error message ")
(write msg)
(display " does not match ")
(write e-msg)
(newline)
#f)))])
(let ([t ?expr])
(newline)
(display "!!! expected error with message ")
(write msg)
(display " but got result ")
(write t)
(newline)
#f)))])))