Session problem

42 views
Skip to first unread message

Oleg

unread,
Jun 30, 2010, 6:30:54 AM6/30/10
to Compojure, ring-c...@googlegroups.com
I've got this error message:

2010-06-30 14:28:02.808::WARN: EXCEPTION
java.lang.NullPointerException
at ring.middleware.session$wrap_session$fn__4514.invoke(session.clj:
47)
at ring.middleware.cookies$wrap_cookies$fn__4276.invoke(cookies.clj:
124)
at compojure.core$routes$fn__4435$fn__4436.invoke(core.clj:71)
at clojure.core$some.invoke(core.clj:2041)
at compojure.core$routes$fn__4435.invoke(core.clj:71)
at ring.middleware.params$wrap_params$fn__4180.invoke(params.clj:76)
at ring.middleware.cookies$wrap_cookies$fn__4276.invoke(cookies.clj:
124)
at clojure.lang.Var.invoke(Var.java:365)

It begins with wrapping my handlers with wrap-session middleware.

Here's little source snippet to reproduce error (some code was
truncated):

(ns aeon.server
(:require (aeon [config :as config]
[error :as error]
[layout :as layout]
[flexible :as flexible]
[middleware :as mw])
(ring.adapter [jetty :as jetty])
(ring.util [response :as response])
(ring.middleware session file-info))
(:use (compojure [core :only [defroutes GET POST ANY wrap!]])))

(defn- tmp-handler [id session]
(let [old-id (:old-id session)]
{:session {:old-id id}
:body
(str "Hello you have requested template #" id
"<br/> Last time you have asked for #" old-id)}))

(defroutes template-routes
(GET "/template/:id/" {{id "id"} :params session :session}
(tmp-handler id session)))

(wrap! template-routes
mw/wrap-layout
ring.middleware.session/wrap-session)

(defroutes all-routes
template-routes)

(defonce server (jetty/run-jetty #'all-routes {:port 8080 :host
"localhost" :join? false}))

(defn restart []
(.stop server)
(.start server))


- Oleg

James Reeves

unread,
Jun 30, 2010, 7:42:50 AM6/30/10
to ring-c...@googlegroups.com, Compojure
On 30 June 2010 11:30, Oleg <oleg.r...@gmail.com> wrote:
> (defroutes template-routes
>  (GET "/template/:id/" {{id "id"} :params session :session}
>       (tmp-handler id session)))
>
> (wrap! template-routes
>       mw/wrap-layout
>       ring.middleware.session/wrap-session)

Currently, if you're going to wrap a handler in the session
middleware, you need to ensure it does not return nil. I guess I'll
add something in to fix this in Ring, but in general, Ring middleware
expects a valid response map, whilst Compojure will return nil if no
route matches.

Because you haven't added a catch-all 404 route, you'll get that
NullPointerException every time someone accesses a resource other than
"/template/:id/". For instance, perhaps the browser is attempting to
retrieve the favicon.

- James

Oleg

unread,
Jun 30, 2010, 8:21:16 AM6/30/10
to Compojure
I have got this error after accessing /template/12/

but this page also tries to load some css and images, which are served
by ring file handler (i've written post about problem in it)

- Oleg

On 30 июн, 15:42, James Reeves <jree...@weavejester.com> wrote:

James Reeves

unread,
Jun 30, 2010, 9:49:33 AM6/30/10
to comp...@googlegroups.com
On 30 June 2010 08:21, Oleg <oleg.r...@gmail.com> wrote:
> I have got this error after accessing /template/12/

Yes, but in your example code, you don't have a catch-all route.

> but this page also tries to load some css and images, which are served
> by ring file handler (i've written post about problem in it)

I don't see this in your example?

Also, you probably want the compojure.route/files function for serving
static files.

Here's what I think your routes should look like:

(require '[compojure.route :as route])
(use '[clojure.contrib.duck-steams :only file])
(use '[ring.middleware.session :only wrap-session])

(defroutes template-routes
(GET "/template/:id" [id]
(tmp-controller id))

(wrap! template-routes :mw/layout)

(defroutes all-routes
template-routes
(route/files "/")
(route/not-found (file "public/404.html")))

(wrap! all-routes :session)

The route/files function will load files from ./public by default, but
you can override this by adding an option map with {:root
"./your-static-files"}.

We're adding your custom layout middleware to your template-routes,
but the session to all-routes. This ensures the session is global.

Keywords can be used to indicate "wrap-" for the wrap! macro. So
(wrap! x :y) is the same as (wrap! x wrap-y).

- James

Oleg

unread,
Jun 30, 2010, 10:29:14 AM6/30/10
to Compojure
Great! Thank you James!

One question:
Should i wrap route/files with ring.middleware.file-info/wrap-file-
info?
What does it do? And why it doesn't work with my locale?

- Oleg

On 30 июн, 17:49, James Reeves <jree...@weavejester.com> wrote:

James Reeves

unread,
Jun 30, 2010, 12:04:27 PM6/30/10
to comp...@googlegroups.com
On 30 June 2010 10:29, Oleg <oleg.r...@gmail.com> wrote:
> One question:
> Should i wrap route/files with ring.middleware.file-info/wrap-file-
> info?
> What does it do? And why it doesn't work with my locale?

wrap-file-info guesses the mime-type from the file extension, and then
adds that to the Content-Type header. That tells the browser what type
of file is being sent.

I'm guessing it doesn't work for you because SimpleDateFormat takes
into current locale, whilst the HTTP date format always uses English
month and day names. I suspect we need to patch Ring to force the date
format to use an English locale.

I'll try to do something about it this weekend, when I'm over my
jetlag. If you can solve this and submit a patch in the meantime,
it'll speed up the process :)

- James

Reply all
Reply to author
Forward
0 new messages