Browse Learn Clojure Foundations as a Java Developer

Avoid Clojure Macro Pitfalls

Learn the macro bugs Java engineers most often miss in Clojure: repeated evaluation, variable capture, unreadable expansion, and debugging the wrong thing.

Macro bugs are usually semantic bugs, not syntax bugs. The generated form may compile, but it can evaluate an argument twice, capture a caller’s local, or hide control flow that should have stayed visible.

Pitfall Review question
Repeated evaluation Does the expansion splice a caller expression into more than one runtime position?
Variable capture Does the macro introduce names that could collide with caller code?
Unreadable expansion Can a teammate explain the generated form without trusting the macro name?
Wrong abstraction Would a function, data map, protocol, or type hint solve the problem more plainly?

Read this section as a macro code-review checklist. A useful macro should make the call site simpler without making the generated code mysterious.

In this section

  • Control Evaluation Order in Clojure Macros
    Learn how macro expansion changes argument evaluation compared with Java method calls, and how to avoid repeated side effects in generated Clojure code.
  • Prevent Variable Capture in Clojure Macros
    Learn how Clojure macro hygiene protects caller code from accidental name collisions, and when to use auto-gensyms, explicit gensyms, or intentional caller bindings.
  • Debug Clojure Macros with Expansions
    Learn a practical macro debugging workflow for Clojure: inspect expansions, move runtime work into functions, test edge cases, and compare generated code with the call site.
Revised on Saturday, May 23, 2026