[racket] module+ test... (require rackunit) results in unbound identifier when used in macro
Thanks guys.
I changed it to this:
(define-syntax (define/test stx)
(syntax-parse stx
[(_ (proc:id arg:expr ...)
body:expr ...
#:test test-body:expr ...)
(with-syntax ([id-str (symbol->string (syntax->datum #'proc))]
[ru-require (format-id stx "~a" "rackunit")])
#'(begin
(define (proc arg ...) body ...)
(module+ test
(require ru-require)
(test-case id-str test-body ...))))]))
and it works now. Is that what you meant Carl?
The problem is that check-true (and check-false) are not in scope (as
> you discovered) during expansion.
I'm still a bit confused as to why. I figured the (require rackunit) would
have brought check-true into scope during expansion, much the same as if I
just copied the (begin... form into another file without the macro.
On Wed, Jan 8, 2014 at 2:37 PM, Carl Eastlund <carl.eastlund at gmail.com>wrote:
> I do not suggest rebinding the whole body like that; it could be seriously
> problematic if the user refers to something not viable to the macro
> definition. What you need to rebind is the name "rackunit" itself passed
> to require so that it has the context of the macro application. That way
> the names bound by the require will be visible to the macro user.
> On Jan 8, 2014 5:29 PM, "Stephen Chang" <stchang at ccs.neu.edu> wrote:
>
>> The problem is that check-true (and check-false) are not in scope (as
>> you discovered) during expansion. Here is one way to fix your problem
>> by recapturing the test expressions to have the proper context. You
>> can also use syntax-local-introduce instead of the lambda (someone
>> correct me if this is not proper usage).
>>
>> #lang racket
>> (require (for-syntax syntax/parse))
>>
>> (define-syntax (define/test stx)
>> (syntax-parse stx
>> [(_ (id arg ...) body ... #:test test-body ...)
>> (with-syntax ([id-str (symbol->string (syntax->datum #'id))]
>> [(new-test-body ...)
>> (map
>> (λ (s) (datum->syntax #'here (syntax->datum s)))
>> (syntax->list #'(test-body ...)))])
>> #'(begin
>> (define (id arg ...) body ...)
>> (print id-str)
>> (module+ test
>> (require rackunit)
>> (test-case id-str
>> new-test-body ...))))]))
>>
>> (define/test (my-fn a b c)
>> (print a)
>> (print b)
>> (print c)
>> #:test
>> (check-true #t)
>> (check-false #t))
>>
>> On Wed, Jan 8, 2014 at 4:53 PM, Scott Klarenbach <scott at pointyhat.ca>
>> wrote:
>> > I have the following macro:
>> >
>> > (define-syntax (define/test stx)
>> > (syntax-parse stx
>> > [(_ (id arg ...) body ... #:test test-body ...)
>> > (with-syntax ([id-str (symbol->string (syntax->datum #'id))])
>> > #'(begin
>> > (define (id arg ...) body ...)
>> > (print id-str)
>> > (module+ test
>> > (require rackunit)
>> > (test-case id-str
>> > test-body ...))))]))
>> >
>> > Which handles some testing boilerplate and allows me to use it like so:
>> >
>> > (define/test (my-fn a b c)
>> > (print a)
>> > (print b)
>> > (print c)
>> > #:test
>> > (check-true #t)
>> > (check-false #t))
>> >
>> > The problem is that the (require rackunit) expression inside of (module+
>> > test) is not being picked up after macro expansion. Running either the
>> code
>> > or the tests (via raco test) results in: unbound identifier check-true.
>> >
>> > Adding (module+ (require rackunit)) to the top of the file solves the
>> > problem and both the file and tests run as expected.
>> >
>> > What am I missing?
>> >
>> > Thanks.
>> > --
>> > Talk to you soon,
>> >
>> > Scott Klarenbach
>> >
>> > PointyHat Software Corp.
>> > www.pointyhat.ca
>> > p 604-568-4280
>> > e scott at pointyhat.ca
>> > 200-1575 W. Georgia
>> > Vancouver, BC V6G2V3
>> >
>> > _______________________________________
>> > To iterate is human; to recur, divine
>> >
>> > ____________________
>> > Racket Users list:
>> > http://lists.racket-lang.org/users
>> >
>>
>> ____________________
>> Racket Users list:
>> http://lists.racket-lang.org/users
>>
>
--
Talk to you soon,
Scott Klarenbach
PointyHat Software Corp.
www.pointyhat.ca
p 604-568-4280
e scott at pointyhat.ca
200-1575 W. Georgia
Vancouver, BC V6G2V3
_______________________________________
To iterate is human; to recur, divine
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.racket-lang.org/users/archive/attachments/20140108/5c75afe8/attachment.html>