Don't use define* and don't use optional. Its too complicated. And don't use set!  As long as you use set! its still has side-effects.  you've got almost the right idea, below is a simpler way of doing it. 

Anyway, look at  http://mitpress.mit.edu/sicp/  ... its free to download.  Reading the first few chapters of this book can be very eye-opening, it broadened my horizons with regard to what software really is.

The usual style looks more like this:
(define (rand-str len)
   (define (get-rand-char) (...whatever...)) 
   (define (helper len  str)
      (if (> len 0)
          ; if len is non-zero, call helper:
          (helper 
              (- len 1) ; shorten len by one.
              (string-append str (get-rand-char))  ; lengthen string by one.
          )
          str  ; return str if len is zero.
   )
   (helper len "")  ;; call the helper function
)

This should work. There are surely more efficient ways to do this, since string manipulation is such a common thing. But the above works, so if its not a bottleneck, its good enough.