I just set up Zope 2.6.1 and am trying to migrate a static web site to it. The site has some navigation links on the right and across the top. The links to the right are different depending on the page content. The links across the top are always the same. Basic tree structure is: www.foo.com/ www.foo.com/company-info/ www.foo.com/company-info/contact www.foo.com/company-info/history www.foo.com/products/ www.foo.com/products/product-1 www.foo.com/products/product-2 www.foo.com/products/product-3 www.foo.com/projects/project-1 www.foo.com/projects/project-2 www.foo.com/projects/project-3 The "contact" and "history" links appear to the right on the "company-info" page. The "product-1", "product-2", and "product-3" links appear to the right on the "products" page, etc. The "company-info", "products", and "projects" links would appear across the top. Is it possible to have one ZPT template which provides dynamic content based on the URL? -- albert chin (china@thewrittenword.com)
On Thu, Aug 28, 2003 at 09:14:53AM -0500, Albert Chin wrote:
I just set up Zope 2.6.1 and am trying to migrate a static web site to it. The site has some navigation links on the right and across the top. The links to the right are different depending on the page content. The links across the top are always the same.
Basic tree structure is: www.foo.com/ www.foo.com/company-info/ www.foo.com/company-info/contact www.foo.com/company-info/history www.foo.com/products/ www.foo.com/products/product-1 www.foo.com/products/product-2 www.foo.com/products/product-3 www.foo.com/projects/project-1 www.foo.com/projects/project-2 www.foo.com/projects/project-3
The "contact" and "history" links appear to the right on the "company-info" page. The "product-1", "product-2", and "product-3" links appear to the right on the "products" page, etc.
The "company-info", "products", and "projects" links would appear across the top.
Is it possible to have one ZPT template which provides dynamic content based on the URL?
Normally this is done by using acquisition. There's a lot of variants, but my favorite ways to solve this kind of problem are A) CMF (but that's pretty involved, and actually your specific request is not trivial for a newbie in the stock CMF setup); or B) use a one-folder-per-page paradigm. This is quite flexible, simple, and should be easy to teach to a content administrator. So, assuming the latter, in your root folder, you set up an index_html template that looks a bit like this (simplified): <!-- begin template --> <div> <!-- common top-nav links go here --> </div> <div tal:content="structure here/content"> The actual page content will be rendered here </div> <div metal:use-macro="here/right_nav/macros/main"> This will be replaced with the right nav macro which you can override per folder. </div> <!-- end template --> Now, create your products and company-info folders. In each folder, create a document (can be a ZPT, a DTML method, or any other suitable object) called "content". This will be the content that gets placed in the middle of the index_html in each folder. Now create the right nav for the products/ folder. To do this, just create a ZPT called products/right_nav. It should look something like: <!-- begin template --> <html> <body> <div metal:define-macro="main"> <a href="/products/product-1"> Product 1 </a> ... </div> </body> </html> <!-- end template --> Do the same in the company-info folder. You'll need a default right_nav in the root folder, too. Presto, your framework is done. Now you can create the individual leaf pages. To do so, simply: 1) create a folder, e.g. products/product-1 2) in this folder, create an object named "content" The reason I'd use the tal:content="structure ..." idiom for the central content, rather than using a METAL macro, is that it's simpler and more flexible for the content manager. When creating or editing content, they only have to create an object named "content" in the appropriate folder; it doesn't matter if it's a ZPT or a DTML method, and they don't have to remember the important detail of using metal:define-macro. You could do the same for the right_nav but in that case I figure it'll be managed by a more zope-savvy person who might like to take advantage of some of METAL's nice features. One gotcha with this approach: You might want to be careful how you set up your ZCatalog, assuming that you use one; you probably don't really want it to return lots of links to things named "content". There are ways, should you need to deal with this... -- Paul Winkler http://www.slinkp.com Look! Up in the sky! It's MY BITCH MEGA! (random hero from isometric.spaceninja.com)
On Thu, Aug 28, 2003 at 11:51:41AM -0400, Paul Winkler wrote:
On Thu, Aug 28, 2003 at 09:14:53AM -0500, Albert Chin wrote:
Basic tree structure is: www.foo.com/ www.foo.com/company-info/ www.foo.com/company-info/contact www.foo.com/company-info/history www.foo.com/products/ www.foo.com/products/product-1 www.foo.com/products/product-2 www.foo.com/products/product-3 www.foo.com/projects/project-1 www.foo.com/projects/project-2 www.foo.com/projects/project-3
The "contact" and "history" links appear to the right on the "company-info" page. The "product-1", "product-2", and "product-3" links appear to the right on the "products" page, etc.
The "company-info", "products", and "projects" links would appear across the top.
Is it possible to have one ZPT template which provides dynamic content based on the URL?
Normally this is done by using acquisition. There's a lot of variants, but my favorite ways to solve this kind of problem are
...
B) use a one-folder-per-page paradigm. This is quite flexible, simple, and should be easy to teach to a content administrator.
So, assuming the latter, in your root folder, you set up an index_html template that looks a bit like this (simplified):
<!-- begin template --> <div> <!-- common top-nav links go here --> </div>
<div tal:content="structure here/content"> The actual page content will be rendered here </div>
<div metal:use-macro="here/right_nav/macros/main"> This will be replaced with the right nav macro which you can override per folder. </div> <!-- end template -->
Now, create your products and company-info folders. In each folder, create a document (can be a ZPT, a DTML method, or any other suitable object) called "content". This will be the content that gets placed in the middle of the index_html in each folder.
Now create the right nav for the products/ folder. To do this, just create a ZPT called products/right_nav. It should look something like:
<!-- begin template --> <html> <body> <div metal:define-macro="main"> <a href="/products/product-1"> Product 1 </a> ... </div> </body> </html> <!-- end template -->
Do the same in the company-info folder. You'll need a default right_nav in the root folder, too.
Presto, your framework is done. Now you can create the individual leaf pages. To do so, simply:
1) create a folder, e.g. products/product-1 2) in this folder, create an object named "content"
...
Thanks. I followed this set up and things are looking good! -- albert chin (china@thewrittenword.com)
<!-- begin template --> <div> <!-- common top-nav links go here --> </div>
<div tal:content="structure here/content"> The actual page content will be rendered here </div>
<div metal:use-macro="here/right_nav/macros/main"> This will be replaced with the right nav macro which you can override per folder. </div> <!-- end template -->
...
Now create the right nav for the products/ folder. To do this, just create a ZPT called products/right_nav. It should look something like:
<!-- begin template --> <html> <body> <div metal:define-macro="main"> <a href="/products/product-1"> Product 1 </a> ... </div> </body> </html> <!-- end template -->
If you wanted dynamic links instead of static, you could use something like this in place of the macro in the template:: <tal:block repeat="link here/links"> <a href="." tal:content="link/title_or_id" tal:attributes="href link/id">link title</a> </tal:block> The 'links' above is a python script that supplies the objects that are valid links. It could be as simple as 'return context.objectValues()' to return all the contents of the folder you are calling the method in. If that folder might have other contents (like 'content'), it might be easiest to make a further subfolder (say 'publish') and use 'return context.publish.objectValues()'. Of course, you could always filter on meta_type like 'return context.objectValues('File')' or any other scheme. --jcc
participants (3)
-
Albert Chin -
J Cameron Cooper -
Paul Winkler