SlideShare una empresa de Scribd logo
1 de 64
Zend Form to the Rescue!
A Brief Introduction to Zend_Form
About Me
Jeremy Kendall
PHP Developer since 2001
Organizer Memphis PHP (MemphisPHP.org)
Contributor to FRAPI project (getFRAPI.com)
jeremy@jeremykendall.net
@JeremyKendall
http://jeremykendall.net
Forms in General
● Ubiquitous
● Tedious
● Challenging to get right
● Security risk
● Primary job responsibility
Typical Form Requirements
● Collect data
● Filter input
● Validate input
● Display validation messages
● Include default data (ex. List of US States)
● Pre-populate fields (for edit/update operations)
● Should be easy to test
● . . . and more.
Typical PHP Form
● Tons of markup
● Tons of code
● Confusing conditionals
● Client side validation likely
● Server side validation?
● Requires two scripts: form & processor
● Not at all easy to test
● I could go on and on . . .
Zend Form to the Rescue!
● Introduced in ZF 1.5, early 2008
● Generates markup
● Filters and validates user input
● Displays validation advice
● Object oriented, easily extended
● Completely customizable
● Can be used apart from ZF MVC
● Easy to test
Standard Form Elements
● Button
● Captcha
● Checkbox
● File
● Hidden
● Hash
● Image
● MultiCheckbox
● MultiSelect
● Password
● Radio
● Reset
● Select
● Text
● TextArea
Standard Filter Classes
● Alnum
● Alpha
● Basename
● Boolean
● HtmlEntities
● StringToLower
● StringToUpper
● StringTrim
● And many more . . .
Standard Validation Classes
● Alnum
● Alpha
● Barcode
● Between
● Callback
● CreditCard
● Date
● Db
● RecordExists
● NoRecordExists
● Digits
● EmailAddress
● File
● Float
● GreaterThan
● Hex
● Hostname
● Iban
● Identical
● And many more . . .
Simple Contact Form
<?php
class Application_Form_Contact extends Zend_Form
{
public function init()
{
// Form elements and such will go here
}
}
Simple Contact Form
<?php
class Application_Form_Contact extends Zend_Form
{
public function init()
{
// Form elements and such will go here
}
}
Simple Contact Form
<?php
class Application_Form_Contact extends Zend_Form
{
public function init()
{
// Form elements and such will go here
}
}
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Name Element
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Your name');
$name->setRequired(true);
$name->addValidators(array(
new Zend_Validate_Regex('/^[- a-z]+$/i'),
new Zend_Validate_StringLength(array('min' => 5))
));
$this->addElement($name);
Email Element
$email = new Zend_Form_Element_Text('email');
$email->setLabel('Email Address');
$email->setRequired(true);
$email->addValidators(array(
new Zend_Validate_EmailAddress(),
new Zend_Validate_StringLength(array('min' => 6))
));
$this->addElement($email);
Email Element
$email = new Zend_Form_Element_Text('email');
$email->setLabel('Email Address');
$email->setRequired(true);
$email->addValidators(array(
new Zend_Validate_EmailAddress(),
new Zend_Validate_StringLength(array('min' => 6))
));
$this->addElement($email);
Message Element
$message = new Zend_Form_Element_Textarea('message');
$message->setLabel('Whatcha got to say?');
$message->setRequired(true);
$message->setAttrib('cols', 40);
$message->setAttrib('rows', 20);
$this->addElement($message);
Message Element
$message = new Zend_Form_Element_Textarea('message');
$message->setLabel('Whatcha got to say?');
$message->setRequired(true);
$message->setAttrib('cols', 40);
$message->setAttrib('rows', 20);
$this->addElement($message);
Submit Element
$submit = new Zend_Form_Element_Submit('submit');
$submit->setLabel('Make contact!');
$submit->setIgnore(true);
$this->addElement($submit);
Submit Element
$submit = new Zend_Form_Element_Submit('submit');
$submit->setLabel('Make contact!');
$submit->setIgnore(true);
$this->addElement($submit);
Add Filters to All Elements
$this->setElementFilters(array(
new Zend_Filter_StringTrim(),
new Zend_Filter_StripTags()
));
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.
}
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.
}
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.
}
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.
}
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.
}
MVC Action
public function indexAction()
{
$form = new Application_Form_Contact();
$this->view->form = $form;
if (!$this->getRequest()->isPost()) {
return;
}
if (!$form->isValid($_POST)) {
return;
}
// Send email, persist data, etc.// Send email, persist data, etc.
}
View
<?php echo $this->form; ?>
Default Markup
<form enctype="application/x-www-form-urlencoded" action=""
method="post">
<dl class="zend_form">
<dt id="name-label">
<label for="name" class="required">Your name</label>
</dt>
<dd id="name-element">
<input type="text" name="name" id="name" value="">
</dd>
. . .
</dl>
</form>
What does it look like?
How about with errors?
Can I use Zend Form by itself?
Standalone - library/base.php
<?php
// Ensure library/ is on include_path
set_include_path(implode(PATH_SEPARATOR, array(
dirname(__FILE__),
get_include_path(),
)));
require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php';
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Application_');
$view = new Zend_View();
Standalone - library/base.php
<?php
// Ensure library/ is on include_path
set_include_path(implode(PATH_SEPARATOR, array(
dirname(__FILE__),
get_include_path(),
)));
require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php';
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Application_');
$view = new Zend_View();
Standalone - library/base.php
<?php
// Ensure library/ is on include_path
set_include_path(implode(PATH_SEPARATOR, array(
dirname(__FILE__),
get_include_path(),
)));
require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php';
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Application_');
$view = new Zend_View();
Standalone - library/base.php
<?php
// Ensure library/ is on include_path
set_include_path(implode(PATH_SEPARATOR, array(
dirname(__FILE__),
get_include_path(),
)));
require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php';
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Application_');
$view = new Zend_View();
Standalone - library/base.php
<?php
// Ensure library/ is on include_path
set_include_path(implode(PATH_SEPARATOR, array(
dirname(__FILE__),
get_include_path(),
)));
require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php';
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Application_');
$view = new Zend_View();
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif ($form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif ($form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif (s$form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif (strtolower($form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif ($form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Standalone – form script
<?php
require_once dirname(__FILE__) . '/library/base.php';
$form = new Application_Form_Contact();
if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' ||
strtolower($_SERVER['REQUEST_METHOD']) == 'post' &&
!$form->isValid($_POST)) {
?>
<!-- Header file might go here -->
<?php echo $form->render($view) ?>
<!-- Footer file might go here -->
<?php
} elseif ($form->isValid($_POST)) {
// Form valid, persist data, send email, etc.
}
Test time!
<?php
/**
* ContactFormTest
*/
class ContactFormTest extends PHPUnit_Framework_TestCase
{
// Setup, teardown, and tests . . .
}
Setting up our test
public function setUp()
{
parent::setUp();
$this->_form = new Application_Form_Contact();
$this->_data = array(
'name' => 'Jeremy Kendall',
'email' => 'jeremy@jeremykendall.net',
'message' => 'Your slides are really, really ugly.'
);
}
Setting up our test
public function setUp()
{
parent::setUp();
$this->_form = new Application_Form_Contact();
$this->_data = array(
'name' => 'Jeremy Kendall',
'email' => 'jeremy@jeremykendall.net',
'message' => 'Your slides are really, really ugly.'
);
}
Setting up our test
public function setUp()
{
parent::setUp();
$this->_form = new Application_Form_Contact();
$this->_data = array(
'name' => 'Jeremy Kendall',
'email' => 'jeremy@jeremykendall.net',
'message' => 'Your slides are really, really ugly.'
);
}
Test Valid Data
public function testValidDataPassesValidation()
{
$this->assertTrue($this->_form->isValid($this->_data));
}
Test Invalid Data
public function testShortNameInvalidatesForm()
{
$this->_data['name'] = 'Bo';
$this->assertFalse($this->_form->isValid($this->_data));
$messages = $this->_form->getMessages();
$this->assertArrayHasKey('name', $messages);
$this->assertArrayHasKey(
'stringLengthTooShort', $messages['name']
);
Test Invalid Data
public function testShortNameInvalidatesForm()
{
$this->_data['name'] = 'Bo';
$this->assertFalse($this->_form->isValid($this->_data));
$messages = $this->_form->getMessages();
$this->assertArrayHasKey('name', $messages);
$this->assertArrayHasKey(
'stringLengthTooShort', $messages['name']
);
Test Invalid Data
public function testShortNameInvalidatesForm()
{
$this->_data['name'] = 'Bo';
$this->assertFalse($this->_form->isValid($this->_data));
$messages = $this->_form->getMessages();
$this->assertArrayHasKey('name', $messages);
$this->assertArrayHasKey(
'stringLengthTooShort', $messages['name']
);
Test Invalid Data
public function testShortNameInvalidatesForm()
{
$this->_data['name'] = 'Bo';
$this->assertFalse($this->_form->isValid($this->_data));
$messages = $this->_form->getMessages();
$this->assertArrayHasKey('name', $messages);
$this->assertArrayHasKey(
'stringLengthTooShort', $messages['name']
);
Test Invalid Data
public function testShortNameInvalidatesForm()
{
$this->_data['name'] = 'Bo';
$this->assertFalse($this->_form->isValid($this->_data));
$messages = $this->_form->getMessages();
$this->assertArrayHasKey('name', $messages);
$this->assertArrayHasKey(
'stringLengthTooShort', $messages['name']
);
PHPUnit Green, my Favorite Color!
Zend Form - Pros
● Object oriented
● Easy input validation
● Easy input filtering
● Markup generation
● Reusable
● Easy to test
Zend Form - Cons
● Learning curve
● Custom layouts can be challenging
● Default markup blows isn't my favorite
Wrapping Up
● Zend Form can save you from form hell
● Powerful in MVC
● Very simple to use outside of MVC
● Easy to test!
Questions?
Resources
● Zend_Form Quickstart
● http://bit.ly/ba8fr0
● Rob Allen's talk, “Working with Zend_Form”
● http://akrabat.com/talks/
● Zend_Form_Element_Multi – Tips and Tricks
● http://bit.ly/bEZl37
Thanks!
Rate this talk: http://joind.in/2388
jeremy@jeremykendall.net
@JeremyKendall
http://jeremykendall.net

Más contenido relacionado

La actualidad más candente

Unit testing with zend framework PHPBenelux
Unit testing with zend framework PHPBeneluxUnit testing with zend framework PHPBenelux
Unit testing with zend framework PHPBeneluxMichelangelo van Dam
 
11. CodeIgniter vederea unei singure inregistrari
11. CodeIgniter vederea unei singure inregistrari11. CodeIgniter vederea unei singure inregistrari
11. CodeIgniter vederea unei singure inregistrariRazvan Raducanu, PhD
 
Система рендеринга в Magento
Система рендеринга в MagentoСистема рендеринга в Magento
Система рендеринга в MagentoMagecom Ukraine
 
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"GeeksLab Odessa
 
Unit testing with zend framework tek11
Unit testing with zend framework tek11Unit testing with zend framework tek11
Unit testing with zend framework tek11Michelangelo van Dam
 
Class 8 - Database Programming
Class 8 - Database ProgrammingClass 8 - Database Programming
Class 8 - Database ProgrammingAhmed Swilam
 
Crafting beautiful software
Crafting beautiful softwareCrafting beautiful software
Crafting beautiful softwareJorn Oomen
 
Gravity Forms Hooks & Filters
Gravity Forms Hooks & FiltersGravity Forms Hooks & Filters
Gravity Forms Hooks & Filtersiamdangavin
 
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)Mark Wilkinson
 
Your code sucks, let's fix it - DPC UnCon
Your code sucks, let's fix it - DPC UnConYour code sucks, let's fix it - DPC UnCon
Your code sucks, let's fix it - DPC UnConRafael Dohms
 
Symfony2 Building on Alpha / Beta technology
Symfony2 Building on Alpha / Beta technologySymfony2 Building on Alpha / Beta technology
Symfony2 Building on Alpha / Beta technologyDaniel Knell
 
Refactoring in Practice - Sunnyconf 2010
Refactoring in Practice - Sunnyconf 2010Refactoring in Practice - Sunnyconf 2010
Refactoring in Practice - Sunnyconf 2010Alex Sharp
 
TDC2016SP - Trilha Developing for Business
TDC2016SP - Trilha Developing for BusinessTDC2016SP - Trilha Developing for Business
TDC2016SP - Trilha Developing for Businesstdc-globalcode
 
Dealing With Legacy PHP Applications
Dealing With Legacy PHP ApplicationsDealing With Legacy PHP Applications
Dealing With Legacy PHP ApplicationsViget Labs
 
Forms, Getting Your Money's Worth
Forms, Getting Your Money's WorthForms, Getting Your Money's Worth
Forms, Getting Your Money's WorthAlex Gaynor
 
Error Reporting in ZF2: form messages, custom error pages, logging
Error Reporting in ZF2: form messages, custom error pages, loggingError Reporting in ZF2: form messages, custom error pages, logging
Error Reporting in ZF2: form messages, custom error pages, loggingSteve Maraspin
 

La actualidad más candente (20)

Rails <form> Chronicle
Rails <form> ChronicleRails <form> Chronicle
Rails <form> Chronicle
 
Unit testing with zend framework PHPBenelux
Unit testing with zend framework PHPBeneluxUnit testing with zend framework PHPBenelux
Unit testing with zend framework PHPBenelux
 
11. CodeIgniter vederea unei singure inregistrari
11. CodeIgniter vederea unei singure inregistrari11. CodeIgniter vederea unei singure inregistrari
11. CodeIgniter vederea unei singure inregistrari
 
Система рендеринга в Magento
Система рендеринга в MagentoСистема рендеринга в Magento
Система рендеринга в Magento
 
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"
QA Lab: тестирование ПО. Яков Крамаренко: "KISS Automation"
 
Unit testing with zend framework tek11
Unit testing with zend framework tek11Unit testing with zend framework tek11
Unit testing with zend framework tek11
 
Class 8 - Database Programming
Class 8 - Database ProgrammingClass 8 - Database Programming
Class 8 - Database Programming
 
Crafting beautiful software
Crafting beautiful softwareCrafting beautiful software
Crafting beautiful software
 
Gravity Forms Hooks & Filters
Gravity Forms Hooks & FiltersGravity Forms Hooks & Filters
Gravity Forms Hooks & Filters
 
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)
SADI in Perl - Protege Plugin Tutorial (fixed Aug 24, 2011)
 
Your code sucks, let's fix it - DPC UnCon
Your code sucks, let's fix it - DPC UnConYour code sucks, let's fix it - DPC UnCon
Your code sucks, let's fix it - DPC UnCon
 
PHP variables
PHP  variablesPHP  variables
PHP variables
 
Symfony2 Building on Alpha / Beta technology
Symfony2 Building on Alpha / Beta technologySymfony2 Building on Alpha / Beta technology
Symfony2 Building on Alpha / Beta technology
 
Refactoring in Practice - Sunnyconf 2010
Refactoring in Practice - Sunnyconf 2010Refactoring in Practice - Sunnyconf 2010
Refactoring in Practice - Sunnyconf 2010
 
TDC2016SP - Trilha Developing for Business
TDC2016SP - Trilha Developing for BusinessTDC2016SP - Trilha Developing for Business
TDC2016SP - Trilha Developing for Business
 
Developing for Business
Developing for BusinessDeveloping for Business
Developing for Business
 
Dealing With Legacy PHP Applications
Dealing With Legacy PHP ApplicationsDealing With Legacy PHP Applications
Dealing With Legacy PHP Applications
 
Forms, Getting Your Money's Worth
Forms, Getting Your Money's WorthForms, Getting Your Money's Worth
Forms, Getting Your Money's Worth
 
Os Nixon
Os NixonOs Nixon
Os Nixon
 
Error Reporting in ZF2: form messages, custom error pages, logging
Error Reporting in ZF2: form messages, custom error pages, loggingError Reporting in ZF2: form messages, custom error pages, logging
Error Reporting in ZF2: form messages, custom error pages, logging
 

Destacado

La Didáctica - Breve resumen
La Didáctica - Breve resumen La Didáctica - Breve resumen
La Didáctica - Breve resumen Alejandro De Greef
 
United States - Making of a Nation
United States - Making of a NationUnited States - Making of a Nation
United States - Making of a NationAlejandro De Greef
 
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...jfsheridan
 
Illinois Health Care Spring It Technology Conference
Illinois Health Care Spring It Technology ConferenceIllinois Health Care Spring It Technology Conference
Illinois Health Care Spring It Technology Conferencejfsheridan
 
Leveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPLeveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPJeremy Kendall
 
Php 102: Out with the Bad, In with the Good
Php 102: Out with the Bad, In with the GoodPhp 102: Out with the Bad, In with the Good
Php 102: Out with the Bad, In with the GoodJeremy Kendall
 
Didactica concepto, objeto y finalidades
Didactica   concepto, objeto y finalidadesDidactica   concepto, objeto y finalidades
Didactica concepto, objeto y finalidadesAlejandro De Greef
 

Destacado (7)

La Didáctica - Breve resumen
La Didáctica - Breve resumen La Didáctica - Breve resumen
La Didáctica - Breve resumen
 
United States - Making of a Nation
United States - Making of a NationUnited States - Making of a Nation
United States - Making of a Nation
 
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...
Navigating Oceans of Data - Being Part of and Competing in the ACO & Bundled ...
 
Illinois Health Care Spring It Technology Conference
Illinois Health Care Spring It Technology ConferenceIllinois Health Care Spring It Technology Conference
Illinois Health Care Spring It Technology Conference
 
Leveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPLeveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHP
 
Php 102: Out with the Bad, In with the Good
Php 102: Out with the Bad, In with the GoodPhp 102: Out with the Bad, In with the Good
Php 102: Out with the Bad, In with the Good
 
Didactica concepto, objeto y finalidades
Didactica   concepto, objeto y finalidadesDidactica   concepto, objeto y finalidades
Didactica concepto, objeto y finalidades
 

Similar a Zend_Form to the Rescue - A Brief Introduction to Zend_Form

Unit testing after Zend Framework 1.8
Unit testing after Zend Framework 1.8Unit testing after Zend Framework 1.8
Unit testing after Zend Framework 1.8Michelangelo van Dam
 
Zend Framework Study@Tokyo #2
Zend Framework Study@Tokyo #2Zend Framework Study@Tokyo #2
Zend Framework Study@Tokyo #2Shinya Ohyanagi
 
Quality assurance for php projects with PHPStorm
Quality assurance for php projects with PHPStormQuality assurance for php projects with PHPStorm
Quality assurance for php projects with PHPStormMichelangelo van Dam
 
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...ZFConf Conference
 
Curso Symfony - Clase 4
Curso Symfony - Clase 4Curso Symfony - Clase 4
Curso Symfony - Clase 4Javier Eguiluz
 
Utilization of zend an ultimate alternate for intense data processing
Utilization of zend  an ultimate alternate for intense data processingUtilization of zend  an ultimate alternate for intense data processing
Utilization of zend an ultimate alternate for intense data processingCareer at Elsner
 
Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Michelangelo van Dam
 
Quality Assurance for PHP projects - ZendCon 2012
Quality Assurance for PHP projects - ZendCon 2012Quality Assurance for PHP projects - ZendCon 2012
Quality Assurance for PHP projects - ZendCon 2012Michelangelo van Dam
 
Getting up & running with zend framework
Getting up & running with zend frameworkGetting up & running with zend framework
Getting up & running with zend frameworkSaidur Rahman
 
Introduction to Zend framework
Introduction to Zend framework Introduction to Zend framework
Introduction to Zend framework Matteo Magni
 
Refactoring using Codeception
Refactoring using CodeceptionRefactoring using Codeception
Refactoring using CodeceptionJeroen van Dijk
 
Zend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolZend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolGordon Forsythe
 
Working With The Symfony Admin Generator
Working With The Symfony Admin GeneratorWorking With The Symfony Admin Generator
Working With The Symfony Admin GeneratorJohn Cleveley
 

Similar a Zend_Form to the Rescue - A Brief Introduction to Zend_Form (20)

Unit testing after Zend Framework 1.8
Unit testing after Zend Framework 1.8Unit testing after Zend Framework 1.8
Unit testing after Zend Framework 1.8
 
Zend Framework Study@Tokyo #2
Zend Framework Study@Tokyo #2Zend Framework Study@Tokyo #2
Zend Framework Study@Tokyo #2
 
Quality assurance for php projects with PHPStorm
Quality assurance for php projects with PHPStormQuality assurance for php projects with PHPStorm
Quality assurance for php projects with PHPStorm
 
Zend Framework
Zend FrameworkZend Framework
Zend Framework
 
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...
ZFConf 2010: Zend Framework & MVC, Model Implementation (Part 2, Dependency I...
 
Curso Symfony - Clase 4
Curso Symfony - Clase 4Curso Symfony - Clase 4
Curso Symfony - Clase 4
 
The new form framework
The new form frameworkThe new form framework
The new form framework
 
Utilization of zend an ultimate alternate for intense data processing
Utilization of zend  an ultimate alternate for intense data processingUtilization of zend  an ultimate alternate for intense data processing
Utilization of zend an ultimate alternate for intense data processing
 
Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12Workshop quality assurance for php projects tek12
Workshop quality assurance for php projects tek12
 
Quality Assurance for PHP projects - ZendCon 2012
Quality Assurance for PHP projects - ZendCon 2012Quality Assurance for PHP projects - ZendCon 2012
Quality Assurance for PHP projects - ZendCon 2012
 
Getting up & running with zend framework
Getting up & running with zend frameworkGetting up & running with zend framework
Getting up & running with zend framework
 
Getting up and running with Zend Framework
Getting up and running with Zend FrameworkGetting up and running with Zend Framework
Getting up and running with Zend Framework
 
Introduction to Zend framework
Introduction to Zend framework Introduction to Zend framework
Introduction to Zend framework
 
Refactoring using Codeception
Refactoring using CodeceptionRefactoring using Codeception
Refactoring using Codeception
 
Zend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_ToolZend Framework 1.9 Setup & Using Zend_Tool
Zend Framework 1.9 Setup & Using Zend_Tool
 
Migrare da symfony 1 a Symfony2
 Migrare da symfony 1 a Symfony2  Migrare da symfony 1 a Symfony2
Migrare da symfony 1 a Symfony2
 
Fatc
FatcFatc
Fatc
 
Drupal 8 migrate!
Drupal 8 migrate!Drupal 8 migrate!
Drupal 8 migrate!
 
Working With The Symfony Admin Generator
Working With The Symfony Admin GeneratorWorking With The Symfony Admin Generator
Working With The Symfony Admin Generator
 
Moodle Quick Forms
Moodle Quick FormsMoodle Quick Forms
Moodle Quick Forms
 

Más de Jeremy Kendall

Leveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPLeveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPJeremy Kendall
 
5 Ways to Awesome-ize Your (PHP) Code
5 Ways to Awesome-ize Your (PHP) Code5 Ways to Awesome-ize Your (PHP) Code
5 Ways to Awesome-ize Your (PHP) CodeJeremy Kendall
 
Game Changing Dependency Management
Game Changing Dependency ManagementGame Changing Dependency Management
Game Changing Dependency ManagementJeremy Kendall
 
Keeping it small - Getting to know the Slim PHP micro framework
Keeping it small - Getting to know the Slim PHP micro frameworkKeeping it small - Getting to know the Slim PHP micro framework
Keeping it small - Getting to know the Slim PHP micro frameworkJeremy Kendall
 
Keeping it Small: Getting to know the Slim Micro Framework
Keeping it Small: Getting to know the Slim Micro FrameworkKeeping it Small: Getting to know the Slim Micro Framework
Keeping it Small: Getting to know the Slim Micro FrameworkJeremy Kendall
 
Keeping it small: Getting to know the Slim micro framework
Keeping it small: Getting to know the Slim micro frameworkKeeping it small: Getting to know the Slim micro framework
Keeping it small: Getting to know the Slim micro frameworkJeremy Kendall
 
PHP 102: Out with the Bad, In with the Good
PHP 102: Out with the Bad, In with the GoodPHP 102: Out with the Bad, In with the Good
PHP 102: Out with the Bad, In with the GoodJeremy Kendall
 
Intro to #memtech PHP 2011-12-05
Intro to #memtech PHP   2011-12-05Intro to #memtech PHP   2011-12-05
Intro to #memtech PHP 2011-12-05Jeremy Kendall
 
TDD in PHP - Memphis PHP 2011-08-25
TDD in PHP - Memphis PHP 2011-08-25TDD in PHP - Memphis PHP 2011-08-25
TDD in PHP - Memphis PHP 2011-08-25Jeremy Kendall
 
Zero to ZF in 10 Minutes
Zero to ZF in 10 MinutesZero to ZF in 10 Minutes
Zero to ZF in 10 MinutesJeremy Kendall
 
Tdd in php a brief example
Tdd in php   a brief exampleTdd in php   a brief example
Tdd in php a brief exampleJeremy Kendall
 
A Brief Introduction to Zend_Form
A Brief Introduction to Zend_FormA Brief Introduction to Zend_Form
A Brief Introduction to Zend_FormJeremy Kendall
 
Zero to Zend Framework in 10 minutes
Zero to Zend Framework in 10 minutesZero to Zend Framework in 10 minutes
Zero to Zend Framework in 10 minutesJeremy Kendall
 

Más de Jeremy Kendall (14)

Leveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHPLeveraging the Power of Graph Databases in PHP
Leveraging the Power of Graph Databases in PHP
 
5 Ways to Awesome-ize Your (PHP) Code
5 Ways to Awesome-ize Your (PHP) Code5 Ways to Awesome-ize Your (PHP) Code
5 Ways to Awesome-ize Your (PHP) Code
 
Game Changing Dependency Management
Game Changing Dependency ManagementGame Changing Dependency Management
Game Changing Dependency Management
 
Keeping it small - Getting to know the Slim PHP micro framework
Keeping it small - Getting to know the Slim PHP micro frameworkKeeping it small - Getting to know the Slim PHP micro framework
Keeping it small - Getting to know the Slim PHP micro framework
 
Keeping it Small: Getting to know the Slim Micro Framework
Keeping it Small: Getting to know the Slim Micro FrameworkKeeping it Small: Getting to know the Slim Micro Framework
Keeping it Small: Getting to know the Slim Micro Framework
 
Keeping it small: Getting to know the Slim micro framework
Keeping it small: Getting to know the Slim micro frameworkKeeping it small: Getting to know the Slim micro framework
Keeping it small: Getting to know the Slim micro framework
 
Php 101: PDO
Php 101: PDOPhp 101: PDO
Php 101: PDO
 
PHP 102: Out with the Bad, In with the Good
PHP 102: Out with the Bad, In with the GoodPHP 102: Out with the Bad, In with the Good
PHP 102: Out with the Bad, In with the Good
 
Intro to #memtech PHP 2011-12-05
Intro to #memtech PHP   2011-12-05Intro to #memtech PHP   2011-12-05
Intro to #memtech PHP 2011-12-05
 
TDD in PHP - Memphis PHP 2011-08-25
TDD in PHP - Memphis PHP 2011-08-25TDD in PHP - Memphis PHP 2011-08-25
TDD in PHP - Memphis PHP 2011-08-25
 
Zero to ZF in 10 Minutes
Zero to ZF in 10 MinutesZero to ZF in 10 Minutes
Zero to ZF in 10 Minutes
 
Tdd in php a brief example
Tdd in php   a brief exampleTdd in php   a brief example
Tdd in php a brief example
 
A Brief Introduction to Zend_Form
A Brief Introduction to Zend_FormA Brief Introduction to Zend_Form
A Brief Introduction to Zend_Form
 
Zero to Zend Framework in 10 minutes
Zero to Zend Framework in 10 minutesZero to Zend Framework in 10 minutes
Zero to Zend Framework in 10 minutes
 

Último

From Family Reminiscence to Scholarly Archive .
From Family Reminiscence to Scholarly Archive .From Family Reminiscence to Scholarly Archive .
From Family Reminiscence to Scholarly Archive .Alan Dix
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteDianaGray10
 
Unleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubUnleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubKalema Edgar
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptx
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptxUse of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptx
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptxLoriGlavin3
 
"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii SoldatenkoFwdays
 
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
DevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenDevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenHervé Boutemy
 
Generative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersGenerative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersRaghuram Pandurangan
 
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024BookNet Canada
 
unit 4 immunoblotting technique complete.pptx
unit 4 immunoblotting technique complete.pptxunit 4 immunoblotting technique complete.pptx
unit 4 immunoblotting technique complete.pptxBkGupta21
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxLoriGlavin3
 
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek SchlawackFwdays
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.Curtis Poe
 
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfHyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfPrecisely
 
SALESFORCE EDUCATION CLOUD | FEXLE SERVICES
SALESFORCE EDUCATION CLOUD | FEXLE SERVICESSALESFORCE EDUCATION CLOUD | FEXLE SERVICES
SALESFORCE EDUCATION CLOUD | FEXLE SERVICESmohitsingh558521
 
What is DBT - The Ultimate Data Build Tool.pdf
What is DBT - The Ultimate Data Build Tool.pdfWhat is DBT - The Ultimate Data Build Tool.pdf
What is DBT - The Ultimate Data Build Tool.pdfMounikaPolabathina
 
What's New in Teams Calling, Meetings and Devices March 2024
What's New in Teams Calling, Meetings and Devices March 2024What's New in Teams Calling, Meetings and Devices March 2024
What's New in Teams Calling, Meetings and Devices March 2024Stephanie Beckett
 
Developer Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLDeveloper Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLScyllaDB
 

Último (20)

From Family Reminiscence to Scholarly Archive .
From Family Reminiscence to Scholarly Archive .From Family Reminiscence to Scholarly Archive .
From Family Reminiscence to Scholarly Archive .
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test Suite
 
Unleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubUnleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding Club
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptx
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptxUse of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptx
Use of FIDO in the Payments and Identity Landscape: FIDO Paris Seminar.pptx
 
"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko"Debugging python applications inside k8s environment", Andrii Soldatenko
"Debugging python applications inside k8s environment", Andrii Soldatenko
 
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
DevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache MavenDevoxxFR 2024 Reproducible Builds with Apache Maven
DevoxxFR 2024 Reproducible Builds with Apache Maven
 
Generative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersGenerative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information Developers
 
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024
New from BookNet Canada for 2024: BNC CataList - Tech Forum 2024
 
unit 4 immunoblotting technique complete.pptx
unit 4 immunoblotting technique complete.pptxunit 4 immunoblotting technique complete.pptx
unit 4 immunoblotting technique complete.pptx
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
 
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
"Subclassing and Composition – A Pythonic Tour of Trade-Offs", Hynek Schlawack
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.
 
DMCC Future of Trade Web3 - Special Edition
DMCC Future of Trade Web3 - Special EditionDMCC Future of Trade Web3 - Special Edition
DMCC Future of Trade Web3 - Special Edition
 
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfHyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
 
SALESFORCE EDUCATION CLOUD | FEXLE SERVICES
SALESFORCE EDUCATION CLOUD | FEXLE SERVICESSALESFORCE EDUCATION CLOUD | FEXLE SERVICES
SALESFORCE EDUCATION CLOUD | FEXLE SERVICES
 
What is DBT - The Ultimate Data Build Tool.pdf
What is DBT - The Ultimate Data Build Tool.pdfWhat is DBT - The Ultimate Data Build Tool.pdf
What is DBT - The Ultimate Data Build Tool.pdf
 
What's New in Teams Calling, Meetings and Devices March 2024
What's New in Teams Calling, Meetings and Devices March 2024What's New in Teams Calling, Meetings and Devices March 2024
What's New in Teams Calling, Meetings and Devices March 2024
 
Developer Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQLDeveloper Data Modeling Mistakes: From Postgres to NoSQL
Developer Data Modeling Mistakes: From Postgres to NoSQL
 

Zend_Form to the Rescue - A Brief Introduction to Zend_Form

  • 1. Zend Form to the Rescue! A Brief Introduction to Zend_Form
  • 2. About Me Jeremy Kendall PHP Developer since 2001 Organizer Memphis PHP (MemphisPHP.org) Contributor to FRAPI project (getFRAPI.com) jeremy@jeremykendall.net @JeremyKendall http://jeremykendall.net
  • 3. Forms in General ● Ubiquitous ● Tedious ● Challenging to get right ● Security risk ● Primary job responsibility
  • 4. Typical Form Requirements ● Collect data ● Filter input ● Validate input ● Display validation messages ● Include default data (ex. List of US States) ● Pre-populate fields (for edit/update operations) ● Should be easy to test ● . . . and more.
  • 5. Typical PHP Form ● Tons of markup ● Tons of code ● Confusing conditionals ● Client side validation likely ● Server side validation? ● Requires two scripts: form & processor ● Not at all easy to test ● I could go on and on . . .
  • 6. Zend Form to the Rescue! ● Introduced in ZF 1.5, early 2008 ● Generates markup ● Filters and validates user input ● Displays validation advice ● Object oriented, easily extended ● Completely customizable ● Can be used apart from ZF MVC ● Easy to test
  • 7. Standard Form Elements ● Button ● Captcha ● Checkbox ● File ● Hidden ● Hash ● Image ● MultiCheckbox ● MultiSelect ● Password ● Radio ● Reset ● Select ● Text ● TextArea
  • 8. Standard Filter Classes ● Alnum ● Alpha ● Basename ● Boolean ● HtmlEntities ● StringToLower ● StringToUpper ● StringTrim ● And many more . . .
  • 9. Standard Validation Classes ● Alnum ● Alpha ● Barcode ● Between ● Callback ● CreditCard ● Date ● Db ● RecordExists ● NoRecordExists ● Digits ● EmailAddress ● File ● Float ● GreaterThan ● Hex ● Hostname ● Iban ● Identical ● And many more . . .
  • 10. Simple Contact Form <?php class Application_Form_Contact extends Zend_Form { public function init() { // Form elements and such will go here } }
  • 11. Simple Contact Form <?php class Application_Form_Contact extends Zend_Form { public function init() { // Form elements and such will go here } }
  • 12. Simple Contact Form <?php class Application_Form_Contact extends Zend_Form { public function init() { // Form elements and such will go here } }
  • 13. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 14. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 15. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 16. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 17. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 18. Name Element $name = new Zend_Form_Element_Text('name'); $name->setLabel('Your name'); $name->setRequired(true); $name->addValidators(array( new Zend_Validate_Regex('/^[- a-z]+$/i'), new Zend_Validate_StringLength(array('min' => 5)) )); $this->addElement($name);
  • 19. Email Element $email = new Zend_Form_Element_Text('email'); $email->setLabel('Email Address'); $email->setRequired(true); $email->addValidators(array( new Zend_Validate_EmailAddress(), new Zend_Validate_StringLength(array('min' => 6)) )); $this->addElement($email);
  • 20. Email Element $email = new Zend_Form_Element_Text('email'); $email->setLabel('Email Address'); $email->setRequired(true); $email->addValidators(array( new Zend_Validate_EmailAddress(), new Zend_Validate_StringLength(array('min' => 6)) )); $this->addElement($email);
  • 21. Message Element $message = new Zend_Form_Element_Textarea('message'); $message->setLabel('Whatcha got to say?'); $message->setRequired(true); $message->setAttrib('cols', 40); $message->setAttrib('rows', 20); $this->addElement($message);
  • 22. Message Element $message = new Zend_Form_Element_Textarea('message'); $message->setLabel('Whatcha got to say?'); $message->setRequired(true); $message->setAttrib('cols', 40); $message->setAttrib('rows', 20); $this->addElement($message);
  • 23. Submit Element $submit = new Zend_Form_Element_Submit('submit'); $submit->setLabel('Make contact!'); $submit->setIgnore(true); $this->addElement($submit);
  • 24. Submit Element $submit = new Zend_Form_Element_Submit('submit'); $submit->setLabel('Make contact!'); $submit->setIgnore(true); $this->addElement($submit);
  • 25. Add Filters to All Elements $this->setElementFilters(array( new Zend_Filter_StringTrim(), new Zend_Filter_StripTags() ));
  • 26. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc. }
  • 27. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc. }
  • 28. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc. }
  • 29. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc. }
  • 30. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc. }
  • 31. MVC Action public function indexAction() { $form = new Application_Form_Contact(); $this->view->form = $form; if (!$this->getRequest()->isPost()) { return; } if (!$form->isValid($_POST)) { return; } // Send email, persist data, etc.// Send email, persist data, etc. }
  • 33. Default Markup <form enctype="application/x-www-form-urlencoded" action="" method="post"> <dl class="zend_form"> <dt id="name-label"> <label for="name" class="required">Your name</label> </dt> <dd id="name-element"> <input type="text" name="name" id="name" value=""> </dd> . . . </dl> </form>
  • 34. What does it look like?
  • 35. How about with errors?
  • 36. Can I use Zend Form by itself?
  • 37. Standalone - library/base.php <?php // Ensure library/ is on include_path set_include_path(implode(PATH_SEPARATOR, array( dirname(__FILE__), get_include_path(), ))); require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php'; $autoloader = Zend_Loader_Autoloader::getInstance(); $autoloader->registerNamespace('Application_'); $view = new Zend_View();
  • 38. Standalone - library/base.php <?php // Ensure library/ is on include_path set_include_path(implode(PATH_SEPARATOR, array( dirname(__FILE__), get_include_path(), ))); require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php'; $autoloader = Zend_Loader_Autoloader::getInstance(); $autoloader->registerNamespace('Application_'); $view = new Zend_View();
  • 39. Standalone - library/base.php <?php // Ensure library/ is on include_path set_include_path(implode(PATH_SEPARATOR, array( dirname(__FILE__), get_include_path(), ))); require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php'; $autoloader = Zend_Loader_Autoloader::getInstance(); $autoloader->registerNamespace('Application_'); $view = new Zend_View();
  • 40. Standalone - library/base.php <?php // Ensure library/ is on include_path set_include_path(implode(PATH_SEPARATOR, array( dirname(__FILE__), get_include_path(), ))); require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php'; $autoloader = Zend_Loader_Autoloader::getInstance(); $autoloader->registerNamespace('Application_'); $view = new Zend_View();
  • 41. Standalone - library/base.php <?php // Ensure library/ is on include_path set_include_path(implode(PATH_SEPARATOR, array( dirname(__FILE__), get_include_path(), ))); require_once dirname(__FILE__) . '/Zend/Loader/Autoloader.php'; $autoloader = Zend_Loader_Autoloader::getInstance(); $autoloader->registerNamespace('Application_'); $view = new Zend_View();
  • 42. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif ($form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 43. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif ($form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 44. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif (s$form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 45. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif (strtolower($form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 46. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif ($form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 47. Standalone – form script <?php require_once dirname(__FILE__) . '/library/base.php'; $form = new Application_Form_Contact(); if (strtolower($_SERVER['REQUEST_METHOD']) == 'get' || strtolower($_SERVER['REQUEST_METHOD']) == 'post' && !$form->isValid($_POST)) { ?> <!-- Header file might go here --> <?php echo $form->render($view) ?> <!-- Footer file might go here --> <?php } elseif ($form->isValid($_POST)) { // Form valid, persist data, send email, etc. }
  • 48. Test time! <?php /** * ContactFormTest */ class ContactFormTest extends PHPUnit_Framework_TestCase { // Setup, teardown, and tests . . . }
  • 49. Setting up our test public function setUp() { parent::setUp(); $this->_form = new Application_Form_Contact(); $this->_data = array( 'name' => 'Jeremy Kendall', 'email' => 'jeremy@jeremykendall.net', 'message' => 'Your slides are really, really ugly.' ); }
  • 50. Setting up our test public function setUp() { parent::setUp(); $this->_form = new Application_Form_Contact(); $this->_data = array( 'name' => 'Jeremy Kendall', 'email' => 'jeremy@jeremykendall.net', 'message' => 'Your slides are really, really ugly.' ); }
  • 51. Setting up our test public function setUp() { parent::setUp(); $this->_form = new Application_Form_Contact(); $this->_data = array( 'name' => 'Jeremy Kendall', 'email' => 'jeremy@jeremykendall.net', 'message' => 'Your slides are really, really ugly.' ); }
  • 52. Test Valid Data public function testValidDataPassesValidation() { $this->assertTrue($this->_form->isValid($this->_data)); }
  • 53. Test Invalid Data public function testShortNameInvalidatesForm() { $this->_data['name'] = 'Bo'; $this->assertFalse($this->_form->isValid($this->_data)); $messages = $this->_form->getMessages(); $this->assertArrayHasKey('name', $messages); $this->assertArrayHasKey( 'stringLengthTooShort', $messages['name'] );
  • 54. Test Invalid Data public function testShortNameInvalidatesForm() { $this->_data['name'] = 'Bo'; $this->assertFalse($this->_form->isValid($this->_data)); $messages = $this->_form->getMessages(); $this->assertArrayHasKey('name', $messages); $this->assertArrayHasKey( 'stringLengthTooShort', $messages['name'] );
  • 55. Test Invalid Data public function testShortNameInvalidatesForm() { $this->_data['name'] = 'Bo'; $this->assertFalse($this->_form->isValid($this->_data)); $messages = $this->_form->getMessages(); $this->assertArrayHasKey('name', $messages); $this->assertArrayHasKey( 'stringLengthTooShort', $messages['name'] );
  • 56. Test Invalid Data public function testShortNameInvalidatesForm() { $this->_data['name'] = 'Bo'; $this->assertFalse($this->_form->isValid($this->_data)); $messages = $this->_form->getMessages(); $this->assertArrayHasKey('name', $messages); $this->assertArrayHasKey( 'stringLengthTooShort', $messages['name'] );
  • 57. Test Invalid Data public function testShortNameInvalidatesForm() { $this->_data['name'] = 'Bo'; $this->assertFalse($this->_form->isValid($this->_data)); $messages = $this->_form->getMessages(); $this->assertArrayHasKey('name', $messages); $this->assertArrayHasKey( 'stringLengthTooShort', $messages['name'] );
  • 58. PHPUnit Green, my Favorite Color!
  • 59. Zend Form - Pros ● Object oriented ● Easy input validation ● Easy input filtering ● Markup generation ● Reusable ● Easy to test
  • 60. Zend Form - Cons ● Learning curve ● Custom layouts can be challenging ● Default markup blows isn't my favorite
  • 61. Wrapping Up ● Zend Form can save you from form hell ● Powerful in MVC ● Very simple to use outside of MVC ● Easy to test!
  • 63. Resources ● Zend_Form Quickstart ● http://bit.ly/ba8fr0 ● Rob Allen's talk, “Working with Zend_Form” ● http://akrabat.com/talks/ ● Zend_Form_Element_Multi – Tips and Tricks ● http://bit.ly/bEZl37
  • 64. Thanks! Rate this talk: http://joind.in/2388 jeremy@jeremykendall.net @JeremyKendall http://jeremykendall.net