Good tab completions means dynamically generated using reflection or whatever (that does not require pre-defined list of completions somewhere) and that knows what can and what can’t follow in particular place.
Like in (.<TAB> x) I’ll get list of methods of x, in (println <TAB>) I get list of local and global definitions, in (Math/<TAB> I get the list of math functions…
For example I like how Tab works in ghci (Haskell) or ipython.
Looks like IClojure does the thing more or less nicely. It is inspired and looks like IPython and offers tab completion (not full, 2 of 3 cases mentioned) and helps developing Clojure in console. Not very stable although.