codestudent
codestudent

Reputation: 73

Why aren't my PHP error messages working correctly?

I'm creating a basic form to purchase adult & child tickets from. With the way the form is set up, the user must purchase an adult ticket, but they don't need to purchase a child ticket. I've added some error messages/validations to enforce rules within the form. All of the adult ticket error messages work correctly, but the child ones aren't working right.

I want the child ticket rules to check the following: that a valid number (aka not a letter) has been entered, the quantity is greater than 0, and a whole number has been entered. I thought I had the rules set so they only start validating if the child ticket input is not empty, but instead they're still trying to validate when it is empty, which I don't want it to do considering no child tickets need to be purchased. How do I get this to work correctly?

Here is my PHP code with the error messages.

<?php
  $adult=$_POST['adult'];
  $child=$_POST['child'];
  $date=date('m/d/Y');

  function isInteger($input) {
    return(ctype_digit(strval($input)));
  }
  if (empty($adult)) {
    $error_message='You must purchase at least 1 Adult ticket!';
  }
  else if (!is_numeric($adult)) {
    $error_message="You must enter a valid number!";
  }
  else if ($adult <= 0) {
    $error_message="You must enter a quantity greater than zero!";
  }
  else if (!isInteger($adult)) {
    $error_message="You must enter a whole number for the quantity! (i.e. 1, 2, etc...)";
  }
  else if (!empty(!is_numeric($child))) {
    $error_message="You must enter a valid number!";
  }
  else if (!empty($child <= 0)) {
    $error_message="You must enter a quantity greater than zero!";
  }
  else if (!empty(!isInteger($child))) {
    $error_message="You must enter a whole number for the quantity! (i.e. 1, 2, etc...)";
  }
  else if ($adult + $child > 5) {
    $error_message="Sorry, there is a limit of 5 total tickets per customer!";
  }
 else {
$error_message='';
  }
  if($error_message !=""){
    include('index.php');
    exit();
  }
?>

Upvotes: 1

Views: 66

Answers (2)

Will B.
Will B.

Reputation: 18426

Not looking for an accepted answer, just wanted to suggest a more practical approach.

PHP has some very powerful built-in functions for validation. Two you can use are filter_var and filter_input, which can easily validate numeric values as integers, without needing to check each variation of an integer.

Additionally instead of chaining several elseif conditions, I suggest using throw to immediately raise an Exception that needs to be handled, otherwise halting execution at that point. Accompanied within a try/catch block to handle the exception as desired.

Example https://3v4l.org/PJfLv

$adult = filter_var($_POST['adult'] ?? null, FILTER_VALIDATE_INT);
$child = filter_var($_POST['child'] ?? null, FILTER_VALIDATE_INT);
try {
    if (false === $adult || false === $child) {
        throw new \InvalidArgumentException('You must enter a whole number (1, 2, etc...)');
    }
    if (0 >= $child || 0 >= $adult) {
        throw new \InvalidArgumentException('You must enter a quantity greater than zero!');
    }
    // at this point child and adult must be >= 1

    // ensure total is at least 1 and at most 5
    $total_options = ['options' => ['min_range' => 1, 'max_range' => 5]];
    $total = filter_var($adult + $child, FILTER_VALIDATE_INT, $total_options);
    if (false === $total) {
        throw new \InvalidArgumentException('Sorry, there is a limit of 5 total tickets per customer!');
    }
    // what should happen next...
} catch(\InvalidArgumentException $e) {
    $error_message = $e->getMessage();
    require __DIR__ . '/index.php'; 
    ## always use absolute paths to prevent include_path overrides/overhead
} finally {
  // do something else no regardless of success or Exception...
}

For PHP < 7.0 replace

$_POST['child']) ?? null

with

isset($_POST['child']) ? $_POST['child'] : null

Upvotes: 0

mrid
mrid

Reputation: 5796

If $child = 1

if(!empty($child <= 0) ) is equivalent to if(!empty(false)) which makes no sense.

Same with (!empty(!is_numeric($child)))

Use if(isset($child) && $child <= 0) {} instead

You can also use $child = isset($_POST['child']) ? $_POST['child'] : 0

Upvotes: 3

Related Questions