我创建了一个类“validate”来验证两个字段,即“firstname”和“lastname”。它工作不正常,当字段为空时它显示错误,但是当我提交包含非空字段的表单时,错误仍然存在。如何在表单提交时执行此操作?
<?php
class validation {
public $firstName, $lastName, $errorFirstName = '', $errorLastName = '';
function __constructor($fName, $lName){
$this->firstName = $fName;
$this->lastName = $lName;
}
function check(){
if($_SERVER["REQUEST_METHOD"] == "POST"){
if(empty($this->firstName)){
$this->errorFirstName = 'First name is required';
} else {
$this->errorFirstName = 'Input is okay';
}
if(empty($this->lastName)){
$this->errorLastName = 'Last name is required';
} else {
$this->errorLastName = 'Input is okay';
}
}
}
}
$obj = new validation($_POST['firstname'], $_POST['lastname']);
$obj->check();
$errorF = $obj->errorFirstName;
$errorL = $obj->errorLastName;
?>
<!DOCTYPE html>
<html lang = "en-US" dir = "ltr">
<head>
<title>Home</title>
<meta charset = "UTF-8"/>
</head>
<body>
<form method = "POST" action="<?php echo $_SERVER["PHP_SELF"]?>">
<label>First Name: </label>
<input type = "text" name = "firstname" placeholder = "John"/>
<p class = "error"><?php echo $errorF;?></p>
<label>Last Name: </label>
<input type = "text" name = "lastname" placeholder = "Doe"/>
<p class = "error"><?php echo $errorL;?></p>
<input type="submit">
</form>
</body>
</html>
大家总是做“数据库类”和“验证类”。呃....什么啊?
不要创建验证类。它永远不会起作用。用于验证用户输入的最.. emm ...可持续选项是:
使用实体进行验证,非常简单。在您的情况下,您将有类
Profile
,其中您有方法 setFirstName(string $name)
。然后在这个方法中,您进行验证,并在出错时抛出自定义的 Exception,例如 InvalidFirstName
.. 或类似的东西。
使用值对象有点棘手,但它可以防止代码重复。例如,您需要验证电子邮件地址。因此,您想要使用它的方式将类似于:
try {
$profile = new Profile;
$profile->setEmail(new EmailAddress($_POST['email']));
} catch (InvalidArgumentException $e){
// validation failed
}
因此,要获得这种行为,您需要像这样定义类:
class EmailAddress
{
private $email;
public function __construct(int $emailId = null, string $email = null)
{
if (!$this->isValid($email)) {
throw new InvalidArgumentException('Not valid email address');
}
$this->email = $email;
}
private function isValid($email)
{
return filter_var($email, FILTER_VALIDATE_EMAIL) !== false;
}
public function __toString()
{
return $this->email;
}
}
这种方法更具表现力,但在与持久层交互时,它往往会变得很粗糙。
在实践中,最好的选择是结合使用这两种解决方案:
创建一个验证器类。
表单通常由多个字段组成,这意味着在建议的方法中,您在设置对象时尝试/捕获错误将在单个字段上失败,当您可能有多个无效字段并且在表单提交时,您希望验证所有字段并且返回所有错误,以便可以同时显示它们。
<?php
class MyValidator
{
/**
* Is form valid;
*
* @var bool
*/
private $isValid = true;
/**
* List of errors, assoc array with error messages one per fieldName
*
* @var array
*/
private $errors = [];
/**
* Check if form is valid
*
* @return bool
*/
public function isValid(): bool
{
return $this->isValid;
}
/**
* Get error message
*
* @param $fieldName
* @return mixed|string
*/
public function getError($fieldName)
{
return isset($this->errors[$fieldName]) ? $this->errors['fieldName'] : '';
}
/**
* @param array $rules list of rules
* @param array $payload list of form parameters
* @return bool Return validation result, same as isValid
*/
public function validate(array $rules, array $payload)
{
foreach ($rules as $rule) {
if (!$this->validateRequired($rule, $payload)) {
continue;
}
switch ($rule['type']) {
case 'string':
$this->validateString($rule, $payload);
break;
case 'email':
$this->validateEmail($rule, $payload);
break;
//extend with other validation rules as needed
}
}
return $this->isValid();
}
public function validateRequired(array $rule, array $payload)
{
if (true === $rule['required'] && !isset($payload[$rule['fieldName']])) {
$this->isValid = false;
$this->errors[$rule['fieldName']] = 'This field is required';
return false;
}
return true;
}
public function validateString($rule, $payload)
{
// Checkup logic, set $this->isValid to false if not valid, add
// See add $this->errors[$rule['fieldname']] = 'your message';
}
public function validateEmail($rule, $payload)
{
// Checkup logic, set $this->isValid to false if not valid, add
// See add $this->errors[$rule['fieldname']] = 'your message';
}
}
// Call validator by giving validator ruleset in the format
$rules = [
[
'fieldName' => 'firstName',
'type' => 'string',
'minLength' => 10,
'maxLength' => 20,
'required' => true,
],
[
'fieldName' => 'email',
'type' => 'email',
'required' => true,
]
];
$validator = new MyValidator();
$isValid = $validator->validate($rules, $_POST);
// if false do repeat form with error messages shown
// use $validator->getError('firstName'); to get error message for a field.
在提到的代码中,其编写方式是在创建类时将表单值传递给类,并且在构造函数内,类变量将使用提供的值进行初始化。
之后 check() 方法将检查字段是否为空。
但这并没有按预期工作,因为从表单传递的值无法初始化为 $firstName 和 $lastName。
原因是,
function __constructor()
不是类的构造函数,它应该是
function __construct()
这就是为什么类变量没有分配表单中给出的值并且出现错误的原因。
修改后问题就解决了。
我正在尝试以这种方式从页面进行验证。
public static function validation($rules)
{
$errors = [];
$all_data = [];
try {
if ($_SERVER['REQUEST_METHOD'] === 'GET') {
$result = str_replace('"', '', $_GET);
} elseif ($_SERVER['REQUEST_METHOD'] === 'POST') {
$result = str_replace('"', '', $_POST);
} elseif ($_SERVER['REQUEST_METHOD'] === 'PUT') {
$result = str_replace('"', '', $_GET);
} elseif ($_SERVER['REQUEST_METHOD'] === 'DELETE') {
$result = str_replace('"', '', $_POST);
}
foreach ($rules as $key => $data) {
$value = explode('|', $data);
$required = preg_match('/required/', $data, $matches) ? $matches[0] : null;
$max = preg_match('/max:(\d+)/', $data, $matches) ? $matches[1] : 256;
$min = preg_match('/min:(\d+)/', $data, $matches) ? $matches[1] : 1;
$unique = preg_match('/unique:(\w+)/', $data, $matches) ? $matches[1] : null;
$email = preg_match('/email/', $data, $matches) ? $matches[0] : null;
if ($required === $value[0]) {
if (empty($result[$key])) {
$errors[$key] = $key . " Is required";
} else {
if ((int)$min >= strlen($result[$key]) || (int)$max <= strlen($result[$key])) $errors[$key] = $key . "Min required or Max required";
if ($email=== $value[0]) {
if (!filter_var($result[$key], FILTER_VALIDATE_EMAIL)) {
$errors[$key] = $key . "Is Email Not Valid";
}
}
if ($unique !== null) {
$data = (new Database())->query("select * from $unique where $key = '$result[$key]'")->get();
if ($data === null) {
$errors[$key] = $key . "Is Unique Value Exists";
}
}
$all_data[$key]= $result[$key];
}
}
}
} catch (\Exception $e) {
echo 'Caught exception: ', $e->getMessage(), "\n";
}
return [
'errors' => $errors,
'data' => $all_data
];
}
给班级打电话,
$validations = Validation::validation([
'name' => 'required|unique:shops|min:1|max:255',
'email' => 'required|unique:shops|min:1|max:255|email'
]);
if ($validations['errors']) {
echo $validations['errors'];
return header('location: /');
}