tapestry-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Don Ryan <don.r...@dit.ie>
Subject Idea for case-insensitive URLs
Date Fri, 26 Jan 2007 12:06:16 GMT

I'd like to float an idea relating to the notion of case in URLs.  
Howard (or whoever) may deem it daft/impractical/whatever but I'll  
float it anyway. The idea stems from two distinct issues. One is a  
long-standing reservation I've had about the appearance of uppercase  
characters in Tapestry URLs and template filenames. The other is the  
recently-mentioned requirement that Howard has for case-insensitivity  
of Tapestry URLs.

Although it's never been anything approaching being a show-stopper,  
the appearance of uppercase characters in Tapestry URLs (in segments  
like page=BookMatches etc.) has always looked odd to me. They are an  
artifact of the capitalization convention used in a particular  
programming language surviving into an entirely different namespace  
(the URL namespace), where, in most circumstances, they tend to be  
rare. Note that such uppercase characters appear even in the  
"friendly URL" alternative. Given that the primary characteristic of  
a friendly URL is to be humanly readable, one good way of assessing a  
URL's friendliness is to try reading it down a phone to someone.  
Having to verbally indicate the case of particular characters is  
awkward and breaks the flow, so is less friendly. For a similar  
reason, HTML designers typically have an in-built aversion to using  
an uppercase character in the filename of something they produce, so  
it seems strange to them that you want a template called  
BookMatches.html. (Certainly in the production of static HTML  
content, it would be very strange to name things like that.) As I  
said, it hasn't been a biggie by any means, but even so I have  
typically tried to allow HTML designers to name templates in the  
manner they would normally prefer. Broadly speaking, there are only  
four main capitalization conventions (omitting schemes that have  
really serious readability problems).

(i) CamelCaseWithUppercaseInitialCharacter
(ii) camelCaseWithLowercaseInitialCharacter
(iv) all_lowercase_with_underscore_separators

Java uses the first three for different kinds of identifier and the  
first for filenames. If a framework required a Java developer to  
adopt something different in any of these cases, the developer would  
probably feel uneasy about doing so. HTML designers (in my  
experience) have a bit of a tendency to favor the fourth convention  
for filenames. Consequently, as a way of avoiding the imposition of a  
new convention on them, I have tended to name pages using (iv) above  
and used the class attribute of the page-specification element to  
specify the corresponding page class, which would obviously use (i)  
above. So, if I use book_matches as the name of the previously  
mentioned page, the template and specification will be  
book_matches.html and book_matches.page respectively, and the latter  
will contain:

<page-specification class="pages.BookMatches">

Now, this is a clear DRY violation, and immediately suggests a  
"convention over configuration" solution. The translation from page  
name to page class name would be trivial to do in code,  stripping  
out underscores and uppercasing certain characters.  All that would  
be required would be to adopt the rule/convention that pages should  
be named using (iv) above and page classes would then have the  
corresponding name using (i) above. The translation would be  
automatic in the framework. (And the greenfield approach to Tapestry  
5 would make this possible.) The neat thing here is that you get case  
insensitivity thrown in for free. It would require nothing more than  
having the translation include the initial step of lowercasing the  
URL segment in question.

In some sense, this approach borrows from one aspect of convention  
over configuration as it is implemented in Rails. The aspect in  
question is that the convention is not a crude "use the same  
identifier" approach, but that the framework undertakes to do the  
translation from what would be a natural identifier in one domain to  
the corresponding natural identifier in another. (E.g. plurals on  
table names becomes singular for class names, as that is more  
natural.) It's this extra level of automatic translation that makes  
the convention over configuration seamless. And, in the above case,  
it buys you case-insensivity for next to nothing.

If the basic idea was deemed to have merit, there is a variation that  
would be worth giving consideration to as well. This would be to have  
the translation include the the extra step of appending a -Page  
suffix to get the page class name (with the corresponding  
modification to the naming convention for page classes). This would  
resolve a minor naming anomaly in Tapestry, whereby a page class, as  
something that represents a page, should naturally be named using a - 
Page suffix. (The anomaly is evident from the fact that the  
historical base classes for page classes, AbstractPage and BasePage,  
do use a -Page suffix, but derived classes do not.) One consequence  
of this naming anomaly is that Tapestry applications have often had  
pairs of classes with the same name, one representing a domain object  
(say Product) and the other representing the page that provides a  
view on that object. To minimize any ambiguity, Tapestry developers  
have resorted to using package names to indicate which is which, say  
model.Product and pages.Product (something which I think is being  
formalized in Tapestry 5). While I favor the idea of standard  
packages, the idea of identically named classes does seem  
unfortunate. The rigorous side of me (which is often absent) would  
want to ask: "What abstraction does this class represent? Does it  
represent a product or a product page?" (And then name it Product or  
ProductPage accordingly.) So a HTML designer could produce  
product.html while the Tapestry developer was working on  
ProductPage.java, and the framework would automatically associate  
them. Something analogous would apply to component classes, although  
I can immediately foresee some people feeling uneasy about that one,  
for no other reason than the character count in the suffix - 
Component. I personally wouldn't have any issue with it as I tend to  
feel that precise naming is more important than saving keystrokes. In  
any case, this is just a variation on the basic idea, which can stand  
on its own.


Don Ryan.

This message has been scanned for content and 
viruses by the DIT Information Services MailScanner 
Service, and is believed to be clean.

To unsubscribe, e-mail: dev-unsubscribe@tapestry.apache.org
For additional commands, e-mail: dev-help@tapestry.apache.org

View raw message