Don Coyote has asked for the wisdom of the Perl Monks concerning the following question:

Hi.

Having some fun with CGI.pm html4 methods.

using CGI I do

use CGI qw/:html4 -no_xhtml/; print $q->(-dtd=>'//W3C//DTD HTML 4.01//EN');

1. Even though I import 4.01 in the dtd of the cgi object I still need to state -no_xhtml after importing CGI otherwise the xmlns namespace appears underneath the html4 strict dtd.

2. After excluding the xmlns namespace I cannot see how to append the html4 strict dtd url on to the dtd so that it reads as required that is

<"//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">

If I try to print it by appending to the dtd like so

print $q->(-dtd=>"'//W3C//DTD HTML 4.01//EN' 'http://www.w3.org/TR/htm +l4/strict.dtd'");

then cgi.pm turns the dtd into the html4 transitional dtd. If I attempt to manually print the dtd prior to using cgi to construct the header the served html fails.

As I need to put this up onto a live server what I need to know is whether the address part of the dtd is important or not. And if it is is there a workaround (or method i'm missing), I kind of always assumed it was as important as the dtd declartion that precedes it.

Replies are listed 'Best First'.
Re: cgi.pm -import strict html4 address into html4 strict dtd header
by Khen1950fx (Canon) on Nov 19, 2011 at 21:48 UTC
    As long as HTML 4.01 is in the -dtd, XHTML is disabled, so you don't need -no_xhmtl. Try this instead.
    #!/usr/bin/perl use strict; use warnings; use CGI qw(:standard :html4); my $q = CGI->new; print $q->start_html(-dtd => '-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/html4/strict.dtd'); print $q->end_html;

      Good solution, but you need brackets around the two parts of the DTD:

      print $q->start_html(-dtd => ['-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/html4/strict.dtd']);

        Of course, I was missing the square brackets!

        After a key value the cgi object expects a closing parens or a comma followed by further key/value pairs. To supply more than one value to a key we require to place multiple values inside an anonymous array, hence placing them inside square brackets. Unless we do this only the first value will be parsed dropping all subsequent values until the next key is reached.

        The importance of the dtd uri is not strictly a perl question granted, however in my assumptions the dtd key would take say '4.01 strict' as a value and proceed to produce the relevant uri namespace. Which would make this more of a cpan query. In the end I was supplying the values incorrectly, so it was a perl question. phew. Reasons for not implementing this behaviour would I expect start with - developer wishes to supply their own dtd.

        As for the browser behaviours MidLifeXis and ww have hit the nail on the head. I'm using IE6. I am developing a website that has marketing towards the national health service (nhs) staff in the uk. This organisation infamously still use ie6 on their workstations. Ie6 is a lot happier when supplied with the correct dtd's.

        But, having corrected the syntax there is still the issue of the xhtml namespace appearing. I think the xhtml namespace is partnered to the xml dtd as the html strict 4 url is partnered to the html 4 strict dtd. Even if the namespace is disabled by supplying the html4 values correctly, unless -no_xhtml is given as an argument to the CGI import, the xmlns namespace line appears in the html header alongside the html4 outputs so we get xmlns:lang='en-GB' and lang='en-GB' attributes inside the html element. Which to me suggests that -no_xhtml must be used when declaring html4 dtd's as it is the solution to the problem or have I found a bug in CGI.pm that needs reporting, go on surely I have(?)!

        use CGI qw/:html4/; print $q->start_html(-lang=>'en-GB', dtd=>['-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/ +html4/strict.dtd']);

        becomes

        <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" lang="en-GB" xml:lang="en-G +B">

        and

        use CGI qw/:html4 -no_xhtml/; print $q->start_html(-lang=>'en-GB', dtd=>['-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/ +html4/strict.dtd']);

        becomes

        <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd"> <html lang="en-GB">

        In reality I think my next step would be to inspect CGI.pm source and see if I can figure out what is going on. however ie6 has several idiosyncracies that I need to contemplate first :(

        many thanks for the perlsyn nudge

        Don Coyote

Re: cgi.pm -import strict html4 address into html4 strict dtd header
by ww (Archbishop) on Nov 19, 2011 at 21:04 UTC
    As is JavaFan, I'm coming up blank on any actual utility in any current browser for the DTD; the DTD's chief value, as far as I can see, is that it's presence in the correct place and format keeps some .html validators from spitting "errors."

    But if you're supporting browsers for those with restricted vision or other physical limitations, you might want to enquire of their user and user-support communities (where such exist) about any use of the DTD.

    Alternately, if you're still supporting Netscape 2.0 or IE 3 or something similar, there may be some merit in using the DTD (but not much value, IMO, in continuing the support). :-)

Re: cgi.pm -import strict html4 address into html4 strict dtd header
by JavaFan (Canon) on Nov 19, 2011 at 19:09 UTC
    As I need to put this up onto a live server what I need to know is whether the address part of the dtd is important or not.
    Whether it's important or not depends on who's parsing the result. I've never heard of a major browser that actually uses the DTD line (that is, render documents differently depending on the DTD settings).

    But the question of the importantness of the DTD line isn't much of a Perl question.