Skip to content

Instantly share code, notes, and snippets.

@MWins
Last active March 3, 2022 16:56
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save MWins/b5202cfd596571da68ce to your computer and use it in GitHub Desktop.
Save MWins/b5202cfd596571da68ce to your computer and use it in GitHub Desktop.
XML-PHP-form-from-file-and-save

Using XML/PHP to generate form, process and store results in XML

creating an MVP where a visitor can edit the information of an existing XML file by adding their name & contact info. I'd like to be able to save the altered xml to a new file and rename it to the visitor's name.

basically this as a starting point: http://stackoverflow.com/questions/12514000/edit-xml-via-html-form-php

Start

Ok this is pretty straight forward but without the existing xml file it's hard to help you. I'll just assume you have an empty xml file with name & contact. It'll look like this :

<contact>
<name></name>
<email></email>
<phone></phone>
</contact>

Now loading this file and displaying form inputs is more complex. What we do is just present the form fields :

<form method="POST" action="process.php" >

<label>Name</label>
<input type="text' name="name" />
<label> Email </label>
<input type="text" name="email" />
<label>Phone </label>
<input type="text" name="phone" />
<input type="submit" value="Save" name="submit"  />
</form>

process.php should be something like the SO you linked .... except I would use $data->asXML('new_filename.xml'); in place of the file creation.

Using XML for the form

Let's take the simple xml file and generate a simple form . The XML source file :

<contact>
<name></name>
<email></email>
<phone></phone>
</contact>

We change form.php to this :

<?php
$form_fields  = null;
$file = 'contact.xml';
$data = simplexml_load_file($file);
foreach($data->children()  as $field)
   {
$form_fields .= '<div>';
$form_fields .=  '<label>' . ucfirst($field->getName()) . ' </label>';
$form_fields .=  '<input type="text" name="'.$field->getName() . '" />';
$form_fields .= '</div>';
}
?>
<!DOCTYPE html>
<html>
<head> 
<style>
form { font-size: 16px; }
form div { margin: .3em; }
legend { font-weight: bold; font-size: 20px; }
label { display:inline-block; width: 140px; }
</style>
</head>
<body>
<form method="POST" action="process.php">
<legend> Enter Contact Information</legend>
<?php echo $form_fields; ?>
<input type="submit" name="submit" value="Submit" class="btn"  />
</form>


</body>
</html>

Now additional elements added to the XML file will generate form inputs. Limited to just text inputs.

Processing hard coded

Following the same format as above, here's a simple processing form. Will post one which uses the XML file afterwards.

This will replace any non alphanumeric characters with an underscore for the submitted data. Not very elegant but is better than nothing for security.

process.php

<?php
if(isset($_POST['submit'])) {
$data=simplexml_load_file('contact.xml');    

if(isset($_POST['email']))    $data->email= preg_replace('/[^a-z0-9]+/i', '_', $_POST['email']);
if(isset($_POST['phone']))    $data->phone= preg_replace('/[^a-z0-9]+/i', '_', $_POST['phone']);

if(isset($_POST['name']))
{
    $contact_name =   preg_replace('/[^a-z0-9]+/i', '_', $_POST['name']);
    $data->name= $contact_name ;
    $new_filename = $contact_name . '.xml';
    $data->asXML($new_filename);
}

}
?>
Form submitted. 

Dynamic Processing

Using the source XML file to power processing. First thing is to change a few requirements. Having the new files created in the same directory is messy IMO. Will put those into a sub directory.

new-process.php

<?php
if(isset($_POST['submit'])) {
$data_dir = 'data/';
$file = 'contact.xml'; 
$data = simplexml_load_file($file); 

foreach($data->children() as $child)
{
$child_name = $child->getName();
if(isset($_POST[$child_name])) $data->{$child_name} = preg_replace('/[^a-z0-9]+/i', '_', $_POST[$child_name]);

}

if(isset($_POST['name']))
{
    $contact_name =   preg_replace('/[^a-z0-9]+/i', '_', $_POST['name']);
    $data->name= $contact_name ;
    $new_filename = $data_dir  . $contact_name . '.xml';
    $data->asXML($new_filename);
}

}

header('Location: form2.php'); 

It works ok. The preg_replace replaces spaces which isn't ideal. Tested by adding a new field to the XML file and it was added to the form and XML output.

I might add viewing and editing the XML files.

Using XSLT to generate FORM

Another option is to use XSLT - Extensible Stylesheet Language Transforms. Bit of a strange method of doing things but tested to work in FF 35.

contact.xml - updated to include linking the xslt file

<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="contact.xsl"?>
    <contact>
    <name></name>
    <email></email>
    <phone></phone>
    <mobile></mobile>
    </contact>

contact.xsl - the XSLT file, doesn't capitalize first letters. Won't accept DOCTYPE either. Form points to the new-process.php which is the later version of process.php (dynamic).

<?xml version="1.0" ?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
	
	<xsl:template match="contact" >
     <xsl:for-each select="*"> 
    <div><label><xsl:value-of select ="name(.)"/></label>
		<input type="text" name="{name(.)}" />
        </div>
        </xsl:for-each>
	</xsl:template>
	<xsl:template match="/">
        <html>
        <head> 
        <style>
        form { font-size: 16px; }
        form div { margin: .3em; }
        legend { font-weight: bold; font-size: 20px; }
        label { display:inline-block; width: 140px; }
        </style>
        </head>
        <body>
        <form method="POST" action="new-process.php">
        <legend>Enter Contact Information</legend>
		<xsl:apply-templates/>
        
        <input type="submit" name="submit" value="Submit" />
        </form>
		</body>
		</html>
	</xsl:template>
	
</xsl:stylesheet>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment