Finished the validation changes.
Ticket: 150
This commit is contained in:
parent
42f7cb706f
commit
db25f46e52
@ -244,6 +244,11 @@ abstract class Doctrine_Record extends Doctrine_Access implements Countable, Ite
|
|||||||
$validator = new Doctrine_Validator();
|
$validator = new Doctrine_Validator();
|
||||||
$validator->validateRecord($this);
|
$validator->validateRecord($this);
|
||||||
$this->validate();
|
$this->validate();
|
||||||
|
if ($this->state == self::STATE_TDIRTY || $this->state == self::STATE_TCLEAN) {
|
||||||
|
$this->validateOnInsert();
|
||||||
|
} else {
|
||||||
|
$this->validateOnUpdate();
|
||||||
|
}
|
||||||
|
|
||||||
return $this->errorStack->count() == 0 ? true : false;
|
return $this->errorStack->count() == 0 ? true : false;
|
||||||
//$this->errorStack->merge($validator->getErrorStack());
|
//$this->errorStack->merge($validator->getErrorStack());
|
||||||
@ -254,6 +259,18 @@ abstract class Doctrine_Record extends Doctrine_Access implements Countable, Ite
|
|||||||
* validations that are neccessary.
|
* validations that are neccessary.
|
||||||
*/
|
*/
|
||||||
protected function validate() {}
|
protected function validate() {}
|
||||||
|
/**
|
||||||
|
* Empty tempalte method to provide concrete Record classes with the possibility
|
||||||
|
* to hook into the validation procedure only when the record is going to be
|
||||||
|
* updated.
|
||||||
|
*/
|
||||||
|
protected function validateOnUpdate() {}
|
||||||
|
/**
|
||||||
|
* Empty tempalte method to provide concrete Record classes with the possibility
|
||||||
|
* to hook into the validation procedure only when the record is going to be
|
||||||
|
* inserted into the data store the first time.
|
||||||
|
*/
|
||||||
|
protected function validateOnInsert() {}
|
||||||
/**
|
/**
|
||||||
* getErrorStack
|
* getErrorStack
|
||||||
*
|
*
|
||||||
|
@ -10,12 +10,12 @@ class Doctrine_Validator_Regexp {
|
|||||||
public function validate(Doctrine_Record $record, $key, $value, $args) {
|
public function validate(Doctrine_Record $record, $key, $value, $args) {
|
||||||
if(is_array($args)) {
|
if(is_array($args)) {
|
||||||
foreach($args as $regexp) {
|
foreach($args as $regexp) {
|
||||||
if( ! preg_match("/$args/", $value))
|
if( ! preg_match($args, $value))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
if(preg_match("/$args/", $value))
|
if(preg_match($args, $value))
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -10,17 +10,19 @@ class User extends Doctrine_Record {
|
|||||||
$this->hasColumn("email_id","integer");
|
$this->hasColumn("email_id","integer");
|
||||||
$this->hasColumn("created","integer",11);
|
$this->hasColumn("created","integer",11);
|
||||||
}
|
}
|
||||||
|
// Our own validation
|
||||||
|
protected function validate() {
|
||||||
|
if ($this->name == 'God') {
|
||||||
|
// Blasphemy! Stop that! ;-)
|
||||||
|
// syntax: add(<fieldName>, <error code/identifier>)
|
||||||
|
$this->errorStack->add('name', 'forbiddenName');
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
class Email extends Doctrine_Record {
|
class Email extends Doctrine_Record {
|
||||||
public function setTableDefinition() {
|
public function setTableDefinition() {
|
||||||
// validators 'email' and 'unique' used
|
// validators 'email' and 'unique' used
|
||||||
$this->hasColumn("address","string",150, array("email", "unique" => true));
|
$this->hasColumn("address","string",150, array("email", "unique"));
|
||||||
}
|
|
||||||
protected function validate() {
|
|
||||||
if ($this->address !== 'the-only-allowed-mail@address.com') {
|
|
||||||
// syntax: add(<fieldName>, <error code>)
|
|
||||||
$this->errorStack->add('address', 'myCustomErrorCode');
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
?>
|
?>
|
||||||
|
@ -4,6 +4,8 @@ try {
|
|||||||
$user->Email->address = "drink@@notvalid..";
|
$user->Email->address = "drink@@notvalid..";
|
||||||
$user->save();
|
$user->save();
|
||||||
} catch(Doctrine_Validator_Exception $e) {
|
} catch(Doctrine_Validator_Exception $e) {
|
||||||
|
// Note: you could also use $e->getInvalidRecords(). The direct way
|
||||||
|
// used here is just more simple when you know the records you're dealing with.
|
||||||
$userErrors = $user->getErrorStack();
|
$userErrors = $user->getErrorStack();
|
||||||
$emailErrors = $user->Email->getErrorStack();
|
$emailErrors = $user->Email->getErrorStack();
|
||||||
|
|
||||||
|
@ -14,10 +14,15 @@ a predefined validator you have three options:<br />
|
|||||||
<br />
|
<br />
|
||||||
The first two options are advisable if it is likely that the validation is of general use
|
The first two options are advisable if it is likely that the validation is of general use
|
||||||
and is potentially applicable in many situations. In that case it is a good idea to implement
|
and is potentially applicable in many situations. In that case it is a good idea to implement
|
||||||
a new validator. However if the validation is special it is better to use hooks provided by Doctrine.
|
a new validator. However if the validation is special it is better to use hooks provided by Doctrine:<br />
|
||||||
One of these hooks is the validate() method. If you need a special validation in your active record
|
<br />
|
||||||
you can simply override validate() in your active record class (a descendant of Doctrine_Record).
|
- validate() (Executed every time the record gets validated)<br />
|
||||||
Within this method you can use all the power of PHP to validate your fields. When a field
|
- validateOnInsert() (Executed when the record is new and gets validated)<br />
|
||||||
|
- validateOnUpdate() (Executed when the record is not new and gets validated)<br />
|
||||||
|
<br />
|
||||||
|
If you need a special validation in your active record
|
||||||
|
you can simply override one of these methods in your active record class (a descendant of Doctrine_Record).
|
||||||
|
Within thess methods you can use all the power of PHP to validate your fields. When a field
|
||||||
doesnt pass your validation you can then add errors to the record's error stack.
|
doesnt pass your validation you can then add errors to the record's error stack.
|
||||||
The following code snippet shows an example of how to define validators together with custom
|
The following code snippet shows an example of how to define validators together with custom
|
||||||
validation:<br />
|
validation:<br />
|
||||||
|
@ -202,14 +202,17 @@ class Doctrine_ValidatorTestCase extends Doctrine_UnitTestCase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tests whether custom validation through template methods works correctly
|
* Tests whether the validate() callback works correctly
|
||||||
* in descendants of Doctrine_Record.
|
* in descendants of Doctrine_Record.
|
||||||
*/
|
*/
|
||||||
public function testCustomValidation() {
|
public function testValidationHooks() {
|
||||||
$this->manager->setAttribute(Doctrine::ATTR_VLD, true);
|
$this->manager->setAttribute(Doctrine::ATTR_VLD, true);
|
||||||
$user = $this->connection->getTable("User")->find(4);
|
|
||||||
|
// Tests validate() and validateOnInsert()
|
||||||
|
$user = new User();
|
||||||
try {
|
try {
|
||||||
$user->name = "I'm not The Saint";
|
$user->name = "I'm not The Saint";
|
||||||
|
$user->password = "1234";
|
||||||
$user->save();
|
$user->save();
|
||||||
} catch(Doctrine_Validator_Exception $e) {
|
} catch(Doctrine_Validator_Exception $e) {
|
||||||
$this->assertEqual($e->count(), 1);
|
$this->assertEqual($e->count(), 1);
|
||||||
@ -218,15 +221,48 @@ class Doctrine_ValidatorTestCase extends Doctrine_UnitTestCase {
|
|||||||
|
|
||||||
$stack = $invalidRecords[0]->getErrorStack();
|
$stack = $invalidRecords[0]->getErrorStack();
|
||||||
|
|
||||||
$this->assertEqual($stack->count(), 1);
|
$this->assertEqual($stack->count(), 2);
|
||||||
$this->assertTrue(in_array('notTheSaint', $stack['name']));
|
$this->assertTrue(in_array('notTheSaint', $stack['name'])); // validate() hook constraint
|
||||||
|
$this->assertTrue(in_array('pwNotTopSecret', $stack['password'])); // validateOnInsert() hook constraint
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Tests validateOnUpdate()
|
||||||
|
$user = $this->connection->getTable("User")->find(4);
|
||||||
try {
|
try {
|
||||||
$user->name = "The Saint";
|
$user->name = "The Saint"; // Set correct name
|
||||||
|
$user->password = "Top Secret"; // Set correct password
|
||||||
|
$user->loginname = "Somebody"; // Wrong login name!
|
||||||
$user->save();
|
$user->save();
|
||||||
} catch(Doctrine_Validator_Exception $e) {
|
|
||||||
$this->fail();
|
$this->fail();
|
||||||
|
} catch(Doctrine_Validator_Exception $e) {
|
||||||
|
$invalidRecords = $e->getInvalidRecords();
|
||||||
|
$this->assertEqual(count($invalidRecords), 1);
|
||||||
|
|
||||||
|
$stack = $invalidRecords[0]->getErrorStack();
|
||||||
|
|
||||||
|
$this->assertEqual($stack->count(), 1);
|
||||||
|
$this->assertTrue(in_array('notNobody', $stack['loginname'])); // validateOnUpdate() hook constraint
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->manager->setAttribute(Doctrine::ATTR_VLD, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Tests whether the validateOnInsert() callback works correctly
|
||||||
|
* in descendants of Doctrine_Record.
|
||||||
|
*/
|
||||||
|
public function testHookValidateOnInsert() {
|
||||||
|
$this->manager->setAttribute(Doctrine::ATTR_VLD, true);
|
||||||
|
|
||||||
|
$user = new User();
|
||||||
|
$user->password = "1234";
|
||||||
|
|
||||||
|
try {
|
||||||
|
$user->save();
|
||||||
|
$this->fail();
|
||||||
|
} catch (Doctrine_Validator_Exception $ex) {
|
||||||
|
$errors = $user->getErrorStack();
|
||||||
|
$this->assertTrue(in_array('pwNotTopSecret', $errors['password']));
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->manager->setAttribute(Doctrine::ATTR_VLD, false);
|
$this->manager->setAttribute(Doctrine::ATTR_VLD, false);
|
||||||
|
@ -9,7 +9,7 @@ class Entity extends Doctrine_Record {
|
|||||||
public function setTableDefinition() {
|
public function setTableDefinition() {
|
||||||
$this->hasColumn("id","integer",20,"autoincrement|primary");
|
$this->hasColumn("id","integer",20,"autoincrement|primary");
|
||||||
$this->hasColumn("name","string",50);
|
$this->hasColumn("name","string",50);
|
||||||
$this->hasColumn("loginname","string",20,"unique");
|
$this->hasColumn("loginname","string",20, array("unique"));
|
||||||
$this->hasColumn("password","string",16);
|
$this->hasColumn("password","string",16);
|
||||||
$this->hasColumn("type","integer",1);
|
$this->hasColumn("type","integer",1);
|
||||||
$this->hasColumn("created","integer",11);
|
$this->hasColumn("created","integer",11);
|
||||||
@ -104,6 +104,16 @@ class User extends Entity {
|
|||||||
$this->errorStack->add('name', 'notTheSaint');
|
$this->errorStack->add('name', 'notTheSaint');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
public function validateOnInsert() {
|
||||||
|
if ($this->password !== 'Top Secret') {
|
||||||
|
$this->errorStack->add('password', 'pwNotTopSecret');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public function validateOnUpdate() {
|
||||||
|
if ($this->loginname !== 'Nobody') {
|
||||||
|
$this->errorStack->add('loginname', 'notNobody');
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
class Groupuser extends Doctrine_Record {
|
class Groupuser extends Doctrine_Record {
|
||||||
public function setTableDefinition() {
|
public function setTableDefinition() {
|
||||||
@ -421,7 +431,7 @@ class ValidatorTest extends Doctrine_Record {
|
|||||||
$this->hasColumn("myobject", "object", 1000);
|
$this->hasColumn("myobject", "object", 1000);
|
||||||
$this->hasColumn("myinteger", "integer", 11);
|
$this->hasColumn("myinteger", "integer", 11);
|
||||||
$this->hasColumn("myrange", "integer", 11, array('range' => array(4,123)));
|
$this->hasColumn("myrange", "integer", 11, array('range' => array(4,123)));
|
||||||
$this->hasColumn("myregexp", "string", 5, array('regexp' => '^[0-9]+$'));
|
$this->hasColumn("myregexp", "string", 5, array('regexp' => '/^[0-9]+$/'));
|
||||||
|
|
||||||
$this->hasColumn("myemail", "string", 100, "email");
|
$this->hasColumn("myemail", "string", 100, "email");
|
||||||
$this->hasColumn("myemail2", "string", 100, "email|notblank");
|
$this->hasColumn("myemail2", "string", 100, "email|notblank");
|
||||||
|
Loading…
x
Reference in New Issue
Block a user