Witam

Chciałbym przy pomocy PHP-DOM wydobyć pola formularza..
Czyli przerobić wszystkie jego inputy do postaci tablicy, takiej jaką otrzymam w $_POST po jego wysłaniu...

Miałem szczerą nadzieję, że znajde taki skrypcik w komentarzach na php.net, niestety bez powodzenia..

Przy tworzeniu takie skryptu trzeba zadbać o szereg rzeczy:
- jeśli value inputa nie zostało ustawione przy typie checkbox, to value będzie 'on'
- jeśli nazwa inputa jest pusta lub jego 'name' to '[]', lub '[foo]', lub '[]foo', to taki input nie znajdzie swojej reprezentacji w tablicy wynikowej..
- jeżeli pole 'value' elementu 'select' nie zostało ustalone, to jako value bierzemy innerHTML elementu option, wycinająć tagi HTML.
- jeżli nazwa elementu to np. 'boo[][][][foo][][][]', to jego reprezentacja w tablicy wynikowej będzie głęboką, wielowymiarową tablicą.
- i wiele, wiele innych....

Generalnie roboty na tydzień.
Nie opuszcza mnie przeczucie, ze ktoś kiedyś czegoś takiego potrzebował, napisał i upublicznił, tylko nie udaje mi się tego znaleść.

Pomocy.

------------------------------------------------

Czasami spacer i papieros dobrze robi...

Zamiast marwić się o te niuanse, robi to za mnie funkcja parse_str

Gotowy kod wygląda tak:

  1. function dom_form_params(&$form) {
  2. $params = array();
  3.  
  4. $inputList = $form->getElementsByTagName('input');
  5. for ( $i = 0; $i < $inputList->length; $i++ ) {
  6. $input = $inputList->item($i);
  7. if ( '' === $name = $input->getAttribute('name')) {
  8. continue;
  9. }
  10. $type = $input->getAttribute('type');
  11. $value = $input->getAttribute('value');
  12.  
  13. if ( 'checkbox' === $type ) {
  14. if ( true !== $input->hasAttribute('checked')) { // input nie jest zaznaczony, pomijamy..
  15. continue;
  16. }
  17. if ( true !== $input->hasAttribute('value')) {
  18. //TODO: sprawdzić czy hasAttribute działa dla róznych wielkości znaków nazwy atrybutu..
  19. $value = 'on';
  20. }
  21. }
  22. else if ( 'radio' === $type ) {
  23. // Jeśli więcej niż jeden input o tej samej nazwie jest checked, interesuje nas ostatni w kolejności..
  24. $checked = $input->hasAttribute('checked');
  25. if ( true !== $checked ) {
  26. continue;
  27. }
  28. if ( true !== $input->hasAttribute('value')) {
  29. $value = 'on';
  30. }
  31. }
  32. $params[] = "{$name}=".urlencode($value);
  33. }
  34.  
  35. $selectList = $form->getElementsByTagName('select');
  36. for ( $i = 0; $i < $selectList->length; $i++ ) {
  37. $select = $selectList->item($i);
  38. $name = $select->getAttribute('name');
  39. $optionList = $select->getElementsByTagName('option');
  40. for ( $j = 0; $j < $optionList->length; $j++ ) {
  41. $option = $optionList->item($j);
  42. $selected = $option->hasAttribute('selected');
  43.  
  44. $_value = $option->getAttribute('value');
  45. if ( ! $option->hasAttribute('value')) { // jeżeli element nie ma value, value to jego nodeValue..
  46. $_value = trim($option->nodeValue);
  47. }
  48. if ( 0 === $j ) { // jeśli żaden option nie jest selected, to formularz przesyła 'value' pierwszego w kolejności elementu 'option'
  49. $value = $_value;
  50. continue;
  51. }
  52. if ( true !== $selected ) {
  53. continue;
  54. }
  55. $value = $_value;
  56. }
  57. $params[] = "{$name}=".urlencode($value);
  58. }
  59.  
  60. $textareaList = $form->getElementsByTagName('textarea');
  61. for ( $i = 0; $i < $textareaList->length; $i++ ) {
  62. $textarea = $textareaList->item($i);
  63. if ( '' === $name = $textarea->getAttribute('name')) {
  64. continue;
  65. }
  66. $value = $textarea->nodeValue;
  67. $params[] = "{$name}=".urlencode($value);
  68. }
  69.  
  70. $string = implode('&', $params);
  71. $otuput = array();
  72. parse_str($string, $output);
  73.  
  74. return $output;
  75. }