santiagocabrera96
Programming Clojure, Fourth Edition: ex-info should include the cause. (p. 224)
In page 224, the following code is suggested.
(defn load-resource [path]
(try
(if (forbidden? path)
(throw (ex-info "Forbidden resource"
{:status 403 :resource path}))
(slurp path))
(catch java.io.FileNotFoundException e
(throw (ex-info "Missing resource"
{:status 404 :resource path})))
(catch java.io.IOException e
(throw (ex-info "Server error"
{:status 500 :resource path})))))
I’ve seen this in practice a lot and not including the cause when catching an exception generates headaches to debug later.
I’d suggest to do a bit of explanation of adding the cause exception to the ex info in the catch clauses like this:
(defn load-resource [path]
(try
(if (forbidden? path)
(throw (ex-info "Forbidden resource"
{:status 403 :resource path}))
(slurp path))
(catch java.io.FileNotFoundException e
(throw (ex-info "Missing resource"
{:status 404 :resource path}
e)))
(catch java.io.IOException e
(throw (ex-info "Server error"
{:status 500 :resource path}
e)))))
This is really useful for me to add context to exceptions that might happen in calling functions on sequences to understand what element failed.
Here’s a dummy example where I can call a function that might throw, and I would want more context on where it failed, and I can add context to the existing ex-info.
(defn randomly-fails []
(when (> (rand-int 10) 8)
(throw (ex-info "Randomly failed!" {}))))
(run! #(try (randomly-fails)
(catch clojure.lang.ExceptionInfo e
(throw (ex-info (ex-message e)
(assoc (ex-data e) :n %)
e))))
(range 100))
=> #'examples.interop/randomly-fails
Execution error (ExceptionInfo) at examples.interop/randomly-fails (form-init16509100671821839256.clj:3).
Randomly failed!
*e
=>
#error
{:cause "Randomly failed!",
:data {},
:via [{:type clojure.lang.ExceptionInfo,
:message "Randomly failed!",
:data {:n 7},
:at [examples.interop$eval2303$fn__2304 invoke "form-init16509100671821839256.clj" 6]}
{:type clojure.lang.ExceptionInfo,
:message "Randomly failed!",
:data {},
:at [examples.interop$randomly_fails invokeStatic "form-init16509100671821839256.clj" 3]}],
Popular Pragmatic Bookshelf topics
Python Testing With Pytest - Chapter 2, warnings for “unregistered custom marks”
While running the smoke tests in Chapter 2, I get these...
New
The following is cross-posted from the original Ray Tracer Challenge forum, from a post by garfieldnate. I’m cross-posting it so that the...
New
Title: Hands-on Rust: question about get_component (page 295)
(feel free to respond. “You dug you’re own hole… good luck”)
I have somet...
New
This isn’t directly about the book contents so maybe not the right forum…but in some of the code apps (e.g. turbo/06) it sends a TURBO_ST...
New
I am working on the “Your Turn” for chapter one and building out the restart button talked about on page 27. It recommends looking into ...
New
Title: Build a Weather Station with Elixir and Nerves: Problem connecting to Postgres with Grafana on (page 64)
If you follow the defau...
New
Hi, I need some help, I’m new to rust and was learning through your book. but I got stuck at the last stage of distribution. Whenever I t...
New
Modern Front-End Development for Rails - application does not start after run bin/setup (page xviii)
After some hassle, I was able to finally run bin/setup, now I have started the rails server but I get this error message right when I vis...
New
@parrt
In the context of Chapter 4.3, the grammar Java.g4, meant to parse Java 6 compilation units, no longer passes ANTLR (currently 4....
New
Hello @herbert ! Trying to get the very first “Hello, Bracket Terminal!" example to run (p. 53). I develop on an Amazon EC2 instance runn...
New
Other popular topics
I know that -t flag is used along with -i flag for getting an interactive shell. But I cannot digest what the man page for docker run com...
New
From finance to artificial intelligence, genetic algorithms are a powerful tool with a wide array of applications. But you don't need an ...
New
We have a thread about the keyboards we have, but what about nice keyboards we come across that we want? If you have seen any that look n...
New
This looks like a stunning keycap set :orange_heart:
A LEGENDARY KEYBOARD LIVES ON
When you bought an Apple Macintosh computer in the e...
New
Do the test and post your score :nerd_face:
:keyboard:
If possible, please add info such as the keyboard you’re using, the layout (Qw...
New
The V Programming Language
Simple language for building maintainable programs
V is already mentioned couple of times in the forum, but I...
New
If you want a quick and easy way to block any website on your Mac using Little Snitch simply…
File > New Rule:
And select Deny, O...
New
Author Spotlight
Erin Dees
@undees
Welcome to our new author spotlight! We had the pleasure of chatting with Erin Dees, co-author of ...
New
I have always used antique keyboards like Cherry MX 1800 or Cherry MX 8100 and almost always have modified the switches in some way, like...
New
Open-source implementation of the classic GTA engine now running directly in your browser. Experience the reVC technology demo on DOS.Zon...
New
Categories:
Sub Categories:
Popular Portals
- /elixir
- /rust
- /wasm
- /ruby
- /erlang
- /phoenix
- /keyboards
- /python
- /js
- /rails
- /security
- /go
- /swift
- /vim
- /clojure
- /java
- /emacs
- /haskell
- /svelte
- /typescript
- /onivim
- /kotlin
- /c-plus-plus
- /crystal
- /tailwind
- /react
- /gleam
- /ocaml
- /elm
- /flutter
- /vscode
- /ash
- /html
- /deepseek
- /opensuse
- /zig
- /centos
- /php
- /scala
- /react-native
- /lisp
- /sublime-text
- /textmate
- /nixos
- /debian
- /agda
- /django
- /deno
- /kubuntu
- /arch-linux
- /nodejs
- /ubuntu
- /spring
- /revery
- /manjaro
- /lua
- /diversity
- /julia
- /markdown
- /quarkus









