Honza,
Sablotron should actually escape the HTML attributes holding URIs the
way you need. In fact, the code is ready but only used for a different
purpose. So I attach a short patch that should do the job. Apply inside
the engine subdirectory. BTW make sure your output method is html, e.g.
by including <xsl:output method="html"/> in your stylesheet.
Hope this helps,
Tom
Honza Pazdziora wrote:
>
> Hello,
>
> I use Sablotron via AxKit and XML::Sablotron. I try to transform input
>
> <people>
> <person><id>243</id><name>Peter Jones</name></person>
> <person><id>244</id><name>Carol Smith</name></person>
> </people>
> to
> <UL>
> <LI><A HREF="/homepage/?id=243">Peter Jones</A>
> <LI><A HREF="/homepage/?id=244">Carol Smith</A>
> </UL>
>
> This is easy in easy cases.
>
> However, the question is: what is the recommended way of escaping
> the parameters in the URL? Here they are numbers but as they may
> contain anything in other situations, a way of changing
>
> <id>" val "</id>
> to
> "?id=%22+val+%22"
>
> would be needed. Currently (for lack of better idea) I do this by
> postprocessing the output and doing this kind of transformation in
> XPathScript but I wonder if some way of doing this directly in
> Sablotron exists or is planned.
>
> One way I can see is xsl:eval and call either some C or (with
> XML::Sablotron) perl function or evaluation code a la JVS or ASP/VB
> approaches, another way could be using namespaces -- but I honestly
> admit that I don't know how standard compliant these would be.
>
> Any comments would be appreciated,
>
> --
> ------------------------------------------------------------------------
> Honza Pazdziora | [EMAIL PROTECTED] | http://www.fi.muni.cz/~adelton/
> .project: Perl, mod_perl, DBI, Oracle, auth. WWW servers, XML/XSL, ...
> ------------------------------------------------------------------------
Index: output.cpp
===================================================================
RCS file: d:/cvs-master/ga/src/Sablot/engine/output.cpp,v
retrieving revision 1.13
diff -a -u -r1.13 output.cpp
--- output.cpp 2000/09/13 12:04:40 1.13
+++ output.cpp 2000/12/04 21:42:54
@@ -84,6 +84,23 @@
"input", "isindex", "link", "meta", "param", NULL
};
+const char* theURI_HTMLAtts[] =
+{
+ "action", // FORM
+ "archive", // OBJECT
+ "background", // BODY
+ "cite", // BLOCKQUOTE, Q, DEL, INS
+ "classid", // OBJECT
+ "codebase", // OBJECT, APPLET
+ "data", // OBJECT
+ "href", // A, AREA, LINK, BASE
+ "longdesc", // IMG, FRAME, IFRAME
+ "profile", // HEAD
+ "src", // SCRIPT, INPUT, FRAME, IFRAME, IMG
+ "usemap", // IMG, INPUT, OBJECT
+ NULL
+};
+
Bool isEmptyHTMLTag(const Str& name)
{
int ndx = lookupNoCase(name, theEmptyHTML40Tags);
@@ -91,6 +108,15 @@
return !!theEmptyHTML40Tags[ndx];
}
+// this should be improved by checking the name of the parent element
+// see the element names in theURI_HTMLAtts
+Bool isURI_HTMLAtt(const Str& name)
+{
+ int ndx = lookupNoCase(name, theURI_HTMLAtts);
+ // return TRUE iff found
+ return !!theURI_HTMLAtts[ndx];
+}
+
//
// OutputDefinition
//
@@ -353,10 +379,14 @@
E( sendStr(attQName.getPrefix()) );
sendLit(":");
};
- E( sendStr(atts[i] -> key.getLocal()) );
+ const Str& localAttName = atts[i] -> key.getLocal();
+ E( sendStr(localAttName) );
sendLit("=\"");
- E( sendStrEsc(atts[i] -> value,
- method == OUTPUT_HTML ? ESCAPING_HTML_ATTR : ESCAPING_ATTR) );
+ EscMode escapingMode =
+ (method == OUTPUT_HTML ? ESCAPING_HTML_ATTR : ESCAPING_ATTR);
+ if (method == OUTPUT_HTML && isURI_HTMLAtt(localAttName))
+ escapingMode = ESCAPING_HTML_URI;
+ E( sendStrEsc(atts[i] -> value, escapingMode));
sendLit("\"");
};