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

I'm working on a web-based app and have recently added CGI::Ajax to deal with form submissions that need different sets of parameters in different cases. The display side of it works great - as I make selections from the static controls, the appropriate additional controls appear, seeded with the correct data (where applicable), and I can interact with them normally.

However, when I submit the form, only the values of the static fields are sent back. The controls which were added dynamically via CGI::Ajax seem to be ignored. Further details:

The relevant section of the static page source is
<tr><form name=orderform action=crystomere.cgi method=get> <td></td> <td colspan=3> <input type=hidden name=action value=issueorder> <input type=hidden name=id id=unitid value=1891233> <select name=ordertype id=ordertype size=1 style="width:100%" On +MouseUp="order_params(['ordertype', 'unitid'], ['orderparams']);"> <option value=halt>Halt <option value=attack>Attack <option value=capture>Capture <option value=move>Move <option value=rest>Rest <option value=wait>Wait </select> <div id=orderparams></div> </td> <td style="vertical-align:bottom"><input type=submit value='Issue +Order'></td> </form></tr>
Selecting, say, a "Wait" order causes CGI::Ajax to send back the text
<table width=100% border=0> <tr><th width=10%>Duration</th><td><input type=text name=duration styl +e="width:100%"></td></tr> </table>
(which is inserted into the "orderparams" div) but a "submit" then GETs crystomere.cgi?action=issueorder&id=1891233&ordertype=wait - action, id, and ordertype are there, but duration is nowhere to be found.

The Firefox DOM inspector shows that the new field is present, it is within the form tags, and it is named as expected. On the advice of a Java junkie friend, I tried changing the submit control to a plain button which did a JavaScript alert showing the value of the CGI::Ajax-added control, then using JS to perform the actual submit; the alert displayed the correct value, but the value was still not sent back to the server.

I'm pretty well out of ideas on this one. As far as I can determine, everything looks right, both on the Perl side and the HTML side. I assume it must be possible to create new form inputs with CGI::Ajax and have them submitted with the rest of the form, so what am I missing here?

Replies are listed 'Best First'.
Re: Submitting forms with CGI::Ajax-created fields
by ikegami (Patriarch) on Jul 22, 2007 at 05:07 UTC

    I couldn't run your code (seeing as you didn't post it all) so I wrote my own version for testing. I can't reproduce your results using FF2.

    <form name=test action=test.cgi method=get> <select name=ordertype id=ordertype onchange=" document.getElementById('orderparams').innerHTML = ( '<input type=text name=duration>' ); "> <option value=halt>Halt <option value=attack>Attack <option value=capture>Capture <option value=move>Move <option value=rest>Rest <option value=wait>Wait </select> <div id=orderparams></div> <div><input type=submit value='Issue Order'></div> </form>

    After changing the value of the SELECT, putting a foo in the text box that appears and pressing the submit button, FF requested the URI

    .../test.cgi?ordertype=move&duration=foo

    Does the above work for you too?

    Note, the HTML was a local file (file:// scheme). That might make a difference.

      OK, I've got a fairly minimal failing case: Using your HTML snippet in $initial_page worked properly, even with your OnChange handler changed to the CGI::Ajax call, so I added HTML::Template back in, stripped down the actual template and tried again. That lost the duration parameter just like the real version does, but using the HTML::Template-generated page body seems to behave identically, so I've put that in and removed HTML::Template. (I did save the stripped-down template and the data I fed it, just in case, but it seems unlikely to be relevant.)
      Yep, I do get the same results as you from that snippet, both accessing it as a file:// and on http://localhost. So this at least confirms that it's possible to do. Now to just figure out why CGI::Ajax isn't doing it...

      Time to strip things down to a minimal failing case, I suppose.

Re: Submitting forms with CGI::Ajax-created fields
by Cody Pendant (Prior) on Jul 22, 2007 at 21:39 UTC
    According to this thread on another forum it's an issue with Firefox, even a listed bug, but it also suggests it can be solved by simply re-organising your HTML, moving the form opening and closing tags outside the table tags.


    Nobody says perl looks like line-noise any more
    kids today don't know what line-noise IS ...
      Hrmph... Never even considered it might be a Firefox bug... Rearranging things so that the table is inside the form instead of the other way around did the trick (and fortunately there's only one form on that page). Thanks!
        It's not a Firefox bug. It's a bug in your HTML. Specifically, <tr><form name=myform action=test.cgi method=get> is illegal. The TR element can only contain (TH|TD)+. You can make it legal by placing the TABLE inside the FORM, or you can place the FORM inside a TD.