summaryrefslogtreecommitdiff
path: root/src/guile/myra-test-utils.scm
blob: 2508b385112da20391b985e3723f571791e32f34 (about) (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
;;; SPDX-License-Identifier: CC0-1.0
;;;
;;; Copyright (C) 2023, 2025 Wojtek Kosior <koszko@koszko.org>

(define-module (myra-test-utils)
  #:use-module ((srfi srfi-26) #:select(cut))
  #:use-module ((srfi srfi-34) #:select (guard raise))
  #:use-module ((srfi srfi-35) #:select (condition-type? condition-has-type?))
  #:use-module ((srfi srfi-64) #:prefix srfi-64:)
  #:use-module ((ice-9 control) #:select (let/ec))
  #:use-module ((ice-9 match) #:select (match))
  #:use-module ((system repl error-handling)
                #:select (call-with-error-handling))
  #:export (%interactive-debugging

            test-assert
            test-eq
            test-eqv
            test-equal
            test-approximate
            test-error

            test-group

            call-with-fixtures
            with-fixtures
            test-group-with-fixtures))

(define %interactive-debugging
  (make-parameter (not (not (getenv "MYRA_INTERACTIVE_DEBUGGING")))))

(define %stop-on-exception
  (make-parameter (not (not (getenv "MYRA_STOP_ON_EXCEPTION")))))

(define (*wrap-expr thunk)
  (if (%interactive-debugging)
      (call-with-error-handling thunk)
      (thunk)))

(define (*wrap-test thunk)
  (if (%stop-on-exception)
      (thunk)
      (false-if-exception (thunk))))

(define-syntax-rule (wrap-expr test-expr)
  (*wrap-expr (lambda () test-expr)))

(define-syntax-rule (wrap-test test)
  (*wrap-test (lambda () test)))

(define-syntax-rule (test-assert stuff ... test-expr)
  (wrap-test (srfi-64:test-assert stuff ... (wrap-expr test-expr))))

(define-syntax-rule (test-eq stuff ... test-expr)
  (wrap-test (srfi-64:test-eq stuff ... (wrap-expr test-expr))))

(define-syntax-rule (test-eqv stuff ... test-expr)
  (wrap-test (srfi-64:test-eqv stuff ... (wrap-expr test-expr))))

(define-syntax-rule (test-equal stuff ... test-expr)
  (wrap-test (srfi-64:test-equal stuff ... (wrap-expr test-expr))))

(define-syntax-rule (test-approximate stuff ... test-expr error)
  (wrap-test (srfi-64:test-approximate stuff ... (wrap-expr test-expr) error)))

(define %exception-object-indicator
  (gensym))

(define (except-error error-type thunk)
  (match (let/ec escape
           (guard (unexpected-ex (#t
                                  (escape unexpected-ex)))
             (*wrap-expr (lambda ()
                           (guard (ex
                                   ((or (and (condition-type? error-type)
                                             (condition-has-type?
                                              ex error-type))
                                        (and (procedure? error-type)
                                             (error-type ex))
                                        (eq? error-type #t))
                                    (escape (list %exception-object-indicator
                                                  ex))))
                             (const (thunk)))))))
    (((? (cut eq? %exception-object-indicator <>)) ex)
     (raise ex))
    (result
     result)))

(define-syntax test-error
  (syntax-rules ()
    ((test-error test-expr)
     (test-error #t test-expr))
    ((test-error stuff ... error-type test-expr)
     (srfi-64:test-error stuff ... #t
                         (except-error error-type (lambda () test-expr))))))

(define-syntax-rule (test-group stuff ...)
  (wrap-test (srfi-64:test-group stuff ...)))

(define (call-with-fixtures fixtures thunk)
  (match fixtures
    (()
     (thunk))
    ((fixture . rest)
     (fixture (cut call-with-fixtures rest thunk)))))

(define-syntax-rule (with-fixtures fixtures body ...)
  (call-with-fixtures fixtures (lambda () body ...)))

(define-syntax-rule (test-group-with-fixtures name fixtures body ...)
  (with-fixtures fixtures (srfi-64:test-group name body ...)))