Forum OpenACS Improvement Proposals (TIPs): TIP #54 (Approved) Add an adp tag to handle documenting and commenting adp files.

When writing adp files, I've often thought it would be useful to be able to write comments on the markup I'm generating that won't be passed on to the user, like <!-- --> would.

We already have ad_page_contract for tcl files to help us document, in addition to the normal tcl commenting.  In adp, the only way to do similiar code commenting would be to use a <if 0></if>.

I propose a new tag, <doc> (I'm open to suggestions for other names for this tag), that we can use to produce adp documentation that is stripped before being sent on to the user. In the short term, comments between the opening and closing <doc> tag could just be discarded, but in the future, the contents of <doc> could be given more structure to allow browsable adp/tcl documentation (like the no-longer-working .dat extension was designed to do).

<doc> tags, initially, should be under a style guide similiar to ad_page_contract to use metadata definitions like @author, @creation-date, etc.  There are also a growing number of developers begining to use Gnu-Arch for development, and a <doc> tag would allow the possibility of including @arch-tag in adps for version control. In addition, this would allow better inline commenting of things like formtemplates, where adp logic can sometimes be hard to follow.

<%
# This may be the type of
# comment mechanism you are
# looking for...

# The user does not see it
%>

That is one option. However, as I understand it, the best practices recommendations for the project are to not use <% %> and <tcl></tcl> in adp templates if at all possible.

Another option would be, as I mentioned in the proposal, to do something like:

<if 0>
# Here are some comments
# that will be stripped
# before the compiled template
# is sent to the user
</if>

Again, this works, but I think a more generalized commenting mechanism would be beneficial. If this is ultimately rejected by the OCT, your option is probably what I'll use instead.

ns_register_adptag comment /comment my_comment 

proc my_comment {string tagset} {}


#or 

template_tag comment {} {}

Using <%, etc. isn't a good idea, because AOLserver will still have to read and interpret every line of the comment.

Collapse
Posted by Roberto Mello on
Approved. I like the idea, and I think it would add to readability.

-Roberto

Tom,

I don't think that ns_register_adptag fits the bill. For one it documents a tag not a page. Secondly, the comments are not included in the ADP page it self and thus not available to editors like Dreamweaver.

Randy, naming the documentation tag allows us to extract the documentation and include it in the API browser. While TCL/ADP pages are currently not included it could be usefull to list their properties too. aD indended to create a .dat mechanism whereby one could call page 'my_page' as 'my_page.dat' and one would get the aspects of a TCL/ADP pair pertinent to a designer. AFAIK, this was never implemented. Lars' proposal to make the presentation of an OpenACS site more independent from the backend heads in the same direction. (https://openacs.org/forums/message-view?message_id=160479)

Using <doc> would allow us to improve the documentation of the ADP component, use that documentation in the OpenACS API browser or an .dat mechanism. While at the same time make the documentation available in editors like Dreamweaver. Using Dreamweaver templates one can protect the <doc> tag from modification.

/Bart

Actually, Bart, the way I was planning to implement this is by using template_tag, which is (among other things) a quick interface to ns_register_adptag. The parser sees the tag, and passes its contents to a proc, which in this case will ignore them.

The mechanism for grabbing the documentation out of the page and presenting it to the browser is another discussion, but one to definitely keep in mind.

Bart: you might refer to the docs on ns_register_adptag first, my examples are how to define a comment tag (or doc tag), in other words it is easy. After defining (registering) the tag, just use it:

<comment>
@author tom 
@cvs-id $Id$
</comment>

template_tag does a few more nice things on top of ns_register_adptag, but eventually it calls that proc.

Tom, sure that is how you define and include a custom tag in ADP. And yes, I should have read up on ns_registeradp_tag. I misread you post. :)

Ben, my point is that we shouldn't ignore the content of the tag -all the time-. Instead we should make the documentation available to developers/designers. I think that we should at least outline how the ADP documentation can be used. So that when this TIP gets approved we've decided on format that we can later expand upon with ways to display the documentation.

/Bart

Benjamin,

I agree very much we need this.

Do we need any info besides author, date, cvs-id?

Like which CSS classes are being used? Cumbersome, probably not necessary, easier to read the code to find out.

Or which properties from the Tcl file are used? Probably not, we (will) have that in the Tcl file's contract already.

Maybe which Tcl file the template was designed for, if the tcl and adp files are not named and located the same.

/Lars

I think we need two tags, one for comments and one for the "page definition". Also great would be if the page definition tag worked with developer support so that you could tell which .adp files were actually used in constructing the page. Of course we could add that to templating instead I guess but I like having cvs info as well.

As we use more .vuh files, nested masters, and includes it can become quite difficult to tell which .adp/.tcl pairs are being used.

I think the proposal should be a little more concrete but I would approve in any case.

Jeff, you make a good point.  Soon after I posted this TIP I realized breaking things up into two seperate tags would be the better way to do things.

**TIP MODIFICATION**

I propose that we add two adp tags to the toolkit, one to handle a kind of ad_page_contract for adp files, and another to enable inline code comments.

<contract>

This tag will be combine some functionalities from ad_page_contract and ad_proc.  There should only be one contract tag per adp file.  It should include a short description explaining what the adp is used for.  It should also contain attribute identifiers, including the following:

@author -- name and email address of the author.
@creation-date -- date of creation.
@cvs-id --  the expanding $Id$.
@arch-tag -- the unique arch identifier, for those using gnu-arch (tla).

@param -- used for each variable the adp expects, with the variable name and a description (see ad_proc documenation).

@css-class -- the name of the css class and a short description of how it is used.  This will make it easier for those modifying style sheets to know what classes they need to modify to obtain the look they want.

<comment>

This tag will be used for inline code comments in the adp.  No special form is required for using this tag.

Both <contract> and <comment> tags and all of their contents will be removed as the adp is parsed and sent to the broswer.

No one has proposed a reason for including an expensive tag, like <contract> in every template page. The page will be sourced hundreds if not thousands of times when the content of this tag will be useless, yet code will still execute for no purpose. Why not someone comes up with a way of an admin page parsing the adp for comment tags which contain special characters, in a form similar to ad_page_contract, once the usage of this tag spreads around?

Maybe add an attribute usage="contract", or whatever...

My opinion, is just showing the page, with the tag at the top will be enough documentation for most of us. I'm pretty good at parsing out the details myself.

Tom, you are wrong. It's no more expensive than any other tag (and cheaper if you simply discard the data on a production site) and it's only sourced once per interp (since .adp's are compiled).

Jeff, what am I wrong about? That no one has come up with a reason to do this (the parsing part, not the commenting part)? That a contract tag is more expensive than a comment tag? But I guess if you don't have a hundred threads, it wouldn't be sourced as many times per server restart as that, but how many times per restart is the information needed for each visited page?

You could probably add an attribute switch which might avoid most of the cost, and provide some other benefits. I.e

<contract 
  log="Debug|Notice|Warning|None" 
  parsewhen="All|Admin"
>...
Tom,

I'm not proposing that the <contract> contents be parsed on every request.  In almost every case, the <contract> tag would be treated exactly the same as a <comment> tag.  Only in those cases where you were explicitely gathering documentation would the contents need to be parsed.

The reason for the seperate <contract> tag is to be able to identify a more easily parsable style, just like ad_page_contract does.

That no one has come up with a reason to do this (the parsing part, not the commenting part)?
Having some structured data is useful for the pages to be self documenting. Everywhere this is used is useful. We have ad_page_contract, comments on tables and columns in the datamodel, ad_library, and ad_proc documentation but no way currently to document in a structured way on the .adp side. I would think it's obviously a useful thing and I can come up with some more uses:
  • Defining an input contract which validates preconditions for the page (similiar to ad_page_contract)
  • All the stuff listed above with javadoc style tags
  • as a hook for per page testing (so you could synthesize the data required for input w/o needing the supporting tcl to run (so designers could work on a page before the code functions).
In any case, I think you want one heavy weight tag where the contents are held onto so you can do these fancy things, and a comment tag which is an immediate discard in the compiled function.
That a contract tag is more expensive than a comment tag?
The contract tag isn't particularly expensive. Certainly it is no more expensive than having an ad_page_contract documentation clause and likely cheaper than your version with the attributes (since I think a plain tag w/o attributes would parse quicker than one with but both are so fast that it's not material to debate them and I prefer free text for the contract). In terms of whether it's more expensive than a comment tag, in the comment tag when compiled the contents would be immediately discarded whereas with the contract tag, on a site where it was not simply discarded, it would need to put the contents into an nsv which for the proc_doc nsv_set (similiar size to the hypothetical nsv we would use for the contract tag) seems to take 9 microseconds per call as times in the ds shell on a fully loaded server (3736 procs defined with docs).
But I guess if you don't have a hundred threads, it wouldn't be sourced as many times per server restart as that, but how many times per restart is the information needed for each visited page?
You can make the exact same argument about ad_page_contract but I don't think many people are in favor of getting rid of the doc clause.
You could probably add an attribute switch which might avoid most of the cost, and provide some other benefits. I.e
<contract 
  log="Debug|Notice|Warning|None" 
  parsewhen="All|Admin"
>...
As mentioned above I doubt this would be faster in any material way and I expect it would be slower.

In ad_page_contract, the docstring isn't parsed every time

    if { [api_page_documentation_mode_p] } {
	# Just gather documentation for this page

        ad_parse_documentation_string $docstring doc_elements
        ...

Whether or not mode switching is faster using a procedure call, as above, or by passing a parameter, I don't know. But I'm sure you are not suggesting the tag run the same way every time, so information has to get in somehow. However parameter passing is the only way to allow easy configuration on a per page basis. Something like documentation_mode would query a global var, whereas other things might benefit from parameters, and some may benefit from package or site-wide settings.

Benjamin,

I don't know how far you're willing to go with this, but...

If we're going to have a "contract" tag it would be good to make it "functional". Right now, there is no enforcement of tcl variable access from the adp. As in, you can declare a variable to be available from the tcl side, but the adp is not limited to the declared vars.

Of course, there should be some indication (switch) that the programmer/designer wants to apply this enforcement, otherwise many things would break.

Well ad_page_contract already has a "properties" attribute, which describes the output variables of the .tcl script.

It's not enforced ... but fixing the issue you raise would, in my mind, be best attacked at making the property tag work.

Approved with two tags, <contract> and <comment>.