Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/260.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 不使用多个返回类型的OOP表单验证_Php_Forms_Oop_Validation - Fatal编程技术网

Php 不使用多个返回类型的OOP表单验证

Php 不使用多个返回类型的OOP表单验证,php,forms,oop,validation,Php,Forms,Oop,Validation,我有一个用户可以登录的程序。我有一个User类,当他们登录时,他们的所有属性(权限、用户名、真实姓名等)都保存为类属性。但是,由于所有数据都需要验证,因此我很难集中精力思考让用户更新自己信息的最佳方法 目前,当用户尝试更新其自己的信息(例如其电子邮件地址)时,我会: // Set new email $try = $user->setEmail($_POST['new_email']); if ($try !== true) { $errors[] = $try; } ... if

我有一个用户可以登录的程序。我有一个
User
类,当他们登录时,他们的所有属性(权限、用户名、真实姓名等)都保存为类属性。但是,由于所有数据都需要验证,因此我很难集中精力思考让用户更新自己信息的最佳方法

目前,当用户尝试更新其自己的信息(例如其电子邮件地址)时,我会:

// Set new email
$try = $user->setEmail($_POST['new_email']);
if ($try !== true) {
    $errors[] = $try;
}
...
if (isset($errors) {
    // Tell user what went wrong
} else {
    $user->saveValuesToDB();
}
它工作正常,但对我来说似乎相当难看,因为
User->setEmail()
需要混合返回类型,因为电子邮件可能因多种原因(未找到域、格式无效、提供的空字符串、其他用户已使用等)而无效,确切原因需要传递回用户,但据我所知,一般不鼓励混合回报

我想到的另一种方法是更新所有属性,而不执行任何类型的验证,然后在最后执行
User->commitAllChanges()
,这将执行所有验证,这将从所有setter方法中获取多个返回,并将其简化为仅提交方法,但我也不喜欢这样,因为我觉得任何实际设置的属性都应该是有效的,而且它仍然不能完全解决这个问题


我可以使用哪些其他方法来允许用户设置对象属性并验证它们,从而将错误发送回用户?或者说我现在做的很好吗?

一种方法是保留您的解决方案(设置电子邮件功能)并使其更加面向对象。 在setAction中,您可以设置错误列表

$this->errors[] = 'Domain invaild';
然后使用1或2个函数从类中获取错误

public function hasErrors() {return false == empty($this->errors);}
public function getErrors() {return $this->errors;}

一种方法是保留您的解决方案(setEmail函数)并使其更加面向对象。 在setAction中,您可以设置错误列表

$this->errors[] = 'Domain invaild';
然后使用1或2个函数从类中获取错误

public function hasErrors() {return false == empty($this->errors);}
public function getErrors() {return $this->errors;}

当前方法没有问题,但可以使用异常

它可能看起来像:

try
{
    $user->setEmail($_POST['new_email']);
}
catch (Exception $e)
{
    $errors[] = $e->getMessage();
}
您的setEmail方法类似于:

setEmail($email)
{
    if ($tooShort) // validate length
        throw new Exception("Email is too short"); // perhaps have custom exceptions
}

当前方法没有问题,但可以使用异常

它可能看起来像:

try
{
    $user->setEmail($_POST['new_email']);
}
catch (Exception $e)
{
    $errors[] = $e->getMessage();
}
您的setEmail方法类似于:

setEmail($email)
{
    if ($tooShort) // validate length
        throw new Exception("Email is too short"); // perhaps have custom exceptions
}
我想到的另一种方法就是更新所有的 属性,而不执行任何类型的验证,然后执行 用户->commitAllChanges()将执行所有 验证,这将从所有 setter方法,并将其简化为仅提交方法

这通常是一个好方法。你也可以把整个过程分解成更小的部分,这样就更通用了

例如,模型可能有一个
validate
方法返回一个布尔值(一切正常吗,还是有一个或多个错误?),还有一个
getValidationErrors
方法返回一个数组,该数组包含您关心的所有信息(可能需要是多维的)。它可以有一个
commit
方法,该方法自动调用
validate
,并且只有在完全没有错误的情况下才会持久化更改

但我也不喜欢这样,因为我觉得 事实上,设置应该是有效的,但它仍然没有完全实现 摆脱这个问题

“无法设置”的属性比人们最初想象的要麻烦得多。主要的问题是,如果属性反对设置(通过返回一些错误代码,或者更好的是通过抛出异常),那么您必须用“保护”代码包装对它的所有访问。这很快就会变得非常乏味

在实践中,更方便的做法是通过一个helper方法为所有属性大规模赋值,然后查看结果(例如,如上所述调用
validate
方法)

另外,不要忘记,在实践中,您可能希望在数据输入字段旁边显示验证错误,并且这些字段被连接为预先填充模型属性的值。因此,一方面属性需要有效,另一方面,它们需要与用户输入的内容完全匹配(否则用户会想要杀死你)。因此,最好放松“必须始终有效”的约束,以支持实用程序——尽管现在到处都是AJAX表单和客户端验证,这一点变得不那么重要了

我想到的另一种方法就是更新所有的 属性,而不执行任何类型的验证,然后执行 用户->commitAllChanges()将执行所有 验证,这将从所有 setter方法,并将其简化为仅提交方法

这通常是一个好方法。你也可以把整个过程分解成更小的部分,这样就更通用了

例如,模型可能有一个
validate
方法返回一个布尔值(一切正常吗,还是有一个或多个错误?),还有一个
getValidationErrors
方法返回一个数组,该数组包含您关心的所有信息(可能需要是多维的)。它可以有一个
commit
方法,该方法自动调用
validate
,并且只有在完全没有错误的情况下才会持久化更改

但我也不喜欢这样,因为我觉得 事实上,设置应该是有效的,但它仍然没有完全实现 摆脱这个问题

“无法设置”的属性比人们最初想象的要麻烦得多。主要的问题是,如果属性反对设置(通过返回一些错误代码,或者更好的是通过抛出异常),那么