We had a problem similar to this and the key is getting the correct data into the Context. What we did was breakout the data creation/Context filling for each view into a separate build-the-context routine. The original views just call their respective routine and then render their template. The composite view calls each of the context-builders and then renders the master template, which then includes the sub-templates.
This is where we ran into a bit of a problem with the Django templating system. We were caching template fragments and some of these fragments took data that was very expensive to generate. If the fragment was not stale, we definitely did not want to do the work. But delaying the work until we knew we needed it meant we were now in the template and:
- You can't pass parameters to methods from within a template.
- The django.template.__init__.Variable._resolve_lookup() method was broken in that if you passed a callable, it wouldn't call it! If you reference a method of an object in the context, that works just fine.
The reason for needing callables to work is that it permits you to pass in a curried function -- i.e. a function that already has some (or all) of its parameters specified, but which has not yet been called. So the view (or the context build in the case) should be able to curry a full-specified function (remember, you can't pass params in the templates themselves) so that the template when it needed to could invoke the callable, get the data, and away we go.
We took two separate approaches to this:
Since we did this site I have learned that we might have been able to solve it by using generators as delayed data producers. The generators act sort of like a curried function (in that you can pass arbitrary params for the setup), but the template engine sees them as just another iterator. There is a great tutorial on this subject. Note: generators are not arrays and you can only consume them once, so some of your logic may need to be tweaked.
Next time I think we'll just go with jinja2 templates and stop screwing with Django's templates.