Forum OpenACS Development: Suggestion: Include src Lookup

Collapse
Posted by Steve Ivy on
I'm just coming to OpenACS, and I've been chatting with some others about how OpenACS does lookups while processing the 'src' attribute of an <include> tag.

From the docs (https://openacs.org/doc/acs-templating/tagref/include.html):

"If the src attribute begins with a slash, the path is assumed to be relative to the server root, the parent directory of the tcl library. If not, the path is assumed to be relative to the current template, not the URL of the page request."

When customizing a package (usually the look and feel), I've found that one usually has to copy large portions of the package because the &lt;include> tags have relative references in the 'src' attribute.

I'd like to suggest that a preliminary step be added to the 'src' processing: before checking the package page_root for the file(s), check the package_url - *then* fall back to the above-described behavior. This means a second lookup in some cases, but in many it means that a developer only has to customize those files directly related to what they're doing.

An example, in the likely case that I'm not being clear:

1) I have an instance of Lars-Blogger mounted at /blog/.

2) In order to customize the appearance of my weblog, I want to change entry_chunk.adp. I don't mind copying entry_chunk.tcl too for now. So I put them in /www/blog/.

3) When the page is served, entry_chunk is included by blog.adp:
    <include src="entry_chunk" etc.>

4) My entry_chunk in /blog/ is ignored - the template processor looks in /packages/lars-blogger/www/  and finds entry_chunk there.

5) In order to modify my entry_chunk, I have to copy over blog.tcl, blog.adp, blog-*.xql, etc. This is not very friendly.

Anyway, what I've suggested is one way to approach the problem. Anyone have any other ideas? I don't imagine I'm the first person to run into this.

Collapse
Posted by Dave Bauer on
I was discussing this with Steve on IRC.

This is another example of the small problem of cusomizing package level code. The toolkit is not designed for non-destructive cusomization.

This is an interesting case, where the main template is fine, but the include needs to be customized. For once, the behavior is well documented. in general I guess we need to be able to access tcl datasource files int he package directory and have them automatically return a customized adp from a package instance specific location.

This might require a change to the request processor to optionally skip standalone ADP files in the overriding directory, grab the package tcl file then ad_return_template would handle the custom adp page.

This would require much less copying where only formatting is changing.

Collapse
Posted by Tom Jackson on

Assuming most customization will be done in the template pages, ad_return_template could be hacked, or just add the correct path to the call to ad_return_template.

For Mydomain.com, I just provided dynamic options to ad_return_template to pick the template I wanted to run based on the Host: header, as well as the requested page. Actually one tcl script served multiple templates in a single instance. So ad_return_template lets you choose the template name, plus the directory of where to get the template. That is one problem I solved without needing to change any core code.

The second issue was the use of the include tag. Although it seems interesting to have a tcl page associated with every template, I have a very complex template page that had lots of conditional code. I wanted to have a simple template that could include the different parts in a way easier than using the include tag. Also the include tag has the nasty feature of requiring you to pass all the variables you need to use through to the included template. Since I had perhaps dozens, if not hundreds of variables, I might use, this was impractical. I created a very simple tag that would just evaluate the template at the current level. (This is what I thought include meant, but I guess that tag really functioned more like ns_adp_include, which required you to pass any vars.) Anyway, another problem was the relative/absolute distinction. There was no way to access a template with real absolute filename. So I had to hack how the src attribute worked in things like the master tag. The main problem with my new tag (I think I called it something stupid like 'read'), was that if you changed the sub-template, you needed to touch the main template to kick the cache into reevaluating the templates, that is, the templating system didn't check the mtime of the sub-templates. This really only affects developers, so it isn't a big drawback.

Overall, the package needs to be written to work this way, only minor changes would need to be made to the OpenACS core.

Collapse
Posted by Don Baccus on
On the greenpeace site we solved this problem by hacking ad_return_template, too.
Collapse
Posted by Dave Bauer on
So perhaps as a general solution:

1) add an acs-templating parameter to turn on the feature that will...

2) check for the existence of a package instance parameter that points to an optional adp location so search for adps. If a template exists in the optional location, that one will be served, otherwise, it uses the built in package template.

If there any opinion on whether this should go into the core, or maybe it could be an optional package that could be installed to add the feature to acs-templating.

That opens up the idea of having packages containing smaller pieces of functionality. I think that is probably a good idea to be discussed in another thread.

Collapse
Posted by Steve Ivy on
After thinking about this, I like Dave's proposed solution. It's simple and flexible, and seems unlikely to break existing code. (Always a good thing.)

I'll be the guinea pig if anyone decides to try this out.