Ogeon / rustful

[OUTDATED] A light HTTP framework for Rust
https://docs.rs/rustful
Apache License 2.0
862 stars 51 forks source link

Implement a central resource storage (take 2) #25

Closed Ogeon closed 9 years ago

Ogeon commented 9 years ago

The old central storage/cache was removed because of coherence problems, but it's a very nice feature to have available. The problem with the old system was that it required the Handler trait to be generic (Handler<Cache>), but that did not work together with impl<C, F: Fn(Context<C>, Response)> Handler<C> for F, which allows both functions and closures to be used as handlers.

The good thing about the old system was that it allowed the library user to use their own types for storage without the need to downcast trait object. This can still be achieved by storing the data in the handler (see examples/handler_storage.rs), but that may be cumbersome and strange in some situations. Here are some alternatives that I can think of right now:

Use Any or a similar trait that allows downcasting.

Use AnyMap, TypeMap or HashMap<String, Box<Any>> where each resource is stored by itself.

More ideas are welcome.

Ogeon commented 9 years ago

The alternative of Any feels like the best bet, because of its freedom to overhead ratio. There will be an extra cost for using AnyMap or TypeMap under it, but it's ideally only paid once per handler call so it's hopefully near negligible.

I will implement this in the coming days.

Ogeon commented 9 years ago

Thinking about it, there is not a huge difference between Box<Any> and AnyMap, except for the memory usage and extra level of indirection from the HashMap in AnyMap, and this makes me doubt my decision. Using Box<Any> makes the global data near unusable for filters and third party handlers, because they have to know what it contains. Using AnyMap would instead allow them to define their own data types and the user would just have to put everything together, instead of making some kind of adapter. It might be worth it, after all.

The problem is just that AnyMap is missing the right concurrency features, at the moment, but it's on its way: chris-morgan/anymap#22

It would also be fantastic if it was possible to convert Box<Any> to an AnyMap.