It seems like you are using an ad blocker. To enhance your experience and support our website, please consider:

  1. Signing in to disable ads on our site.
  2. Sign up if you don't have an account yet.
  3. Or, disable your ad blocker by doing this:
    • Click on the ad blocker icon in your browser's toolbar.
    • Select "Pause on this site" or a similar option for lancecourse.com.

Make your first CRUD with PHP - Part 3: CREATE

By zooboole

Hi, welcome to the third part of our tutorial on PHP CRUD. In this part I will be talking of the CREATE. We will discovering or rediscover how that works.

What is create?

In all cases applications are meant to treat/process data. No matter the data the application processes or no matter how it does it, there are some common points any application considers: the data input phase, processing phase, and an output phase.

The input phase consists of the application require some little information in order to give a given feed back. In the case of a website, we usually use forms to ask user to enter their details in order for our application to recognize them as member or other things. Once the application has this information, it has to store this data somewhere, either in a database, a file, in session, or in cookies, etc.

That action of saving the data is called the creation phase, or simply CREATE. In our case here we will be saving our data into a database.

Now that you know what CREATE means in CRUD, let see what we are going to do here. To demonstrate how that is done, I will be developing the option to add a new admin and a product in the database.

In order to accomplish that, I have done some changes to the admin menu which becomes:

<ul>
    <li><a href="dashboard.php">Dashboard</a></li>
    <li><a href="add-admin.php">Add Admin</a></li>
    <li><a href="add-product.php">Add Product</a></li>
    <li><a href="list-products.php">List Products</a></li>
    <li><a href="logout.php">Logout</a></li>
</ul>

You can see here that for each aspect I have prepared a specific file to handle that. I made it this way just to show you step by step the difference between each action.

Add new admin

For this we're going to use the add-admin.php file. We will also need the includes/classes/admin-class.php file because it will contain some common functions to admins.

add-admin.php is going to be at the root of the project. It will contain the form through which the admins can be input.

We have already seen in the previous part how our admin table looks like. It's actually a very minimalistic one. Admins have just a username and a password.

So here are the source codes for each page:

add-admin.php

<?php
    // Start from getting the hader which contains some settings we need
    require_once 'includes/header.php';

    // Redirect visitor to the login page if he is trying to access
    // this page without being logged in
    if (!isset($_SESSION['admin_session']) )
    {
        session::destroy('admin_session');
        $commons->redirectTo(SITE_PATH.'index.php');
    }
?>
<html>
    <head>
        <title>Products Management System | Admin Panel</title>
        <link href='https://fonts.googleapis.com/css?family=Oswald:400,300' rel='stylesheet' type='text/css'>
        <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
        <link rel="stylesheet" href="public/css/CreativeButtons/css/component.css">
        <link rel="stylesheet" href="public/css/style.css">
    </head>

    <body>
        <main class="container">
            <a href="https://lancecourse.com/en/howto/make-your-first-crud-with-php-case-of-a-product-management-system/34" class="btn btn-4 btn-4d icon-arrow-left">Return to tutorial</a>
            <div class="admin-pannel">

                <div class="dashboard">
                    <h3>Add Admin</h3>
                    <hr>
                    <p>Please fill in the form bellow to add a new admin.</p>

                    <?php  if ( isset($_SESSION['errors']) ): ?>
                    <div class="pannel panel-warning">
                        <?php foreach ($_SESSION['errors'] as $error):?>
                            <li><?= $error ?></li>
                        <?php endforeach ?>
                    </div>
                    <?php session::destroy('errors'); endif ?>

                    <?php  if ( isset($_SESSION['confirm']) ): ?>
                    <div class="pannel panel-success">
                        <li><?= $_SESSION['confirm'] ?></li>
                    </div>
                    <?php session::destroy('confirm'); endif ?>

                    <!-- We send the form information to process-new-admin.php to handle it -->
                    <form action="process-new-admin.php" method="POST">
                        <div>
                            <label for="username">New Admin Username</label>
                            <input type="text" name="username" id="username">
                        </div>

                        <div>
                            <label for="password">New Admin Password</label>
                            <input type="password" name="password" id="password">
                        </div>

                        <div>
                            <label for="repassword">Re-enter Password</label>
                            <input type="password" name="repassword" id="repassword">
                        </div>

                        <div class="activate">
                            <button type="submit" class="btn-1a">Save Admin</button>
                        </div>
                    </form>
                </div>
                <aside class="admin-menu">
                    <p>Connected as, <?= strip_tags($_SESSION['admin_session']) ?></p>
                    <ul>
                        <li><a href="dashboard.php">Dashboard</a></li>
                        <li><a href="add-admin.php">Add Admin</a></li>
                        <li><a href="add-product.php">Add Product</a></li>
                        <li><a href="list-products.php">List Products</a></li>
                        <li><a href="logout.php">Logout</a></li>
                    </ul>
                </aside>

                <div style="clear:both"> </div>
            </div>

            <footer>
                <?= date("Y") ?> &copy; lancecourse.com - Project by <a href="http://zooboole.me" target="_blank">zooboole</a> - Credit to <a href="http://tympanus.net/codrops/2013/06/13/creative-button-styles/" target="_blank">tympanus.net</a>
            </footer>
        </main>
    </body>
</html>

process-new-admin.php

<?php

    /*
     * We process the admin login form here
     */

    // Start from getting the hader which contains some settings we need
    require_once 'includes/header.php';

    // require the admins class which containes most functions applied to admins
    require_once ROOT."../includes/classes/admin-class.php";

    $admins     = new Admins($dbh);

    // check if the form is submitted

    if (isset($_POST)) 
    {
        // If the form is submitted

        // first we check if all fields are filled out
        // In our case all fields are required, so we can just loop
        $errors = array();

        foreach($_POST as $key => $value) 
        {
          if(empty($value) || trim($value) == '') {
            $errors[$key] = "The field ".$key." should not be empty.";
          }
          $$key = $value;
        }

        // If there is any error we send back to the form
        if (!empty($errors) || sizeof($errors) != 0) 
        {
            session::set('errors', $errors);
            $commons->redirectTo(SITE_PATH.'add-admin.php');
        }

        // Check if password are the same
        if (!$admins->ArePasswordsSame($_POST['password'], $_POST['repassword'])) 
        {
            session::set('errors', ['The two passwords do not match.']);
            $commons->redirectTo(SITE_PATH.'add-admin.php');
        }

        // From here you can unset the repassword field
        // the password is in $_POST['password']
        unset($_POST['repassword']);

        // Now let's check if another admin is not using the new username already
        if ($admins->adminExists($_POST['username'])) 
        {
            session::set('errors', ['This username is already in use by another admin.']);
            $commons->redirectTo(SITE_PATH.'add-admin.php');
        }

        // We've checked everything, 
        // now we can CREATE the admin in the admins table

        if (!$admins->addNewAdmin($username, $password)) 
        {
            session::set('errors', ['An error occured while saving the new admin.']);
            $commons->redirectTo(SITE_PATH.'add-admin.php');
        }

        // Else we display a confirmation message
        session::set('confirm', 'New admin added successfully!');
        $commons->redirectTo(SITE_PATH.'add-admin.php');

    }

Add new product

This function is the same as adding a new admin. They all show how to CREATE. So I am just adding to satisfy this topic and also I believe someone may like to use it and improve.

add-product.php

<?php
    // Start from getting the hader which contains some settings we need
    require_once 'includes/header.php';

    // Redirect visitor to the login page if he is trying to access
    // this page without being logged in
    if (!isset($_SESSION['admin_session']) )
    {
        session::destroy('admin_session');
        $commons->redirectTo(SITE_PATH.'index.php');
    }
?>
<html>
    <head>
        <title>Products Management System | Admin Panel</title>
        <link href='https://fonts.googleapis.com/css?family=Oswald:400,300' rel='stylesheet' type='text/css'>
        <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
        <link rel="stylesheet" href="public/css/CreativeButtons/css/component.css">
        <link rel="stylesheet" href="public/css/style.css">
    </head>

    <body>
        <main class="container">
            <a href="https://lancecourse.com/en/howto/make-your-first-crud-with-php-case-of-a-product-management-system" class="btn btn-4 btn-4d icon-arrow-left">Return to tutorial</a>
            <div class="admin-pannel">

                <div class="dashboard">
                    <h3>Add A Product</h3>
                    <hr>
                    <p>Please fill in the form bellow to add a new product.</p>

                    <?php  if ( isset($_SESSION['errors']) ): ?>
                    <div class="pannel panel-warning">
                        <?php foreach ($_SESSION['errors'] as $error):?>
                            <li><?= $error ?></li>
                        <?php endforeach ?>
                    </div>
                    <?php session::destroy('errors'); endif ?>

                    <?php  if ( isset($_SESSION['confirm']) ): ?>
                    <div class="pannel panel-success">
                        <li><?= $_SESSION['confirm'] ?></li>
                    </div>
                    <?php session::destroy('confirm'); endif ?>

                    <!-- We send the form information to process-new-admin.php to handle it -->
                    <form action="process-new-product.php" method="POST">
                        <div>
                            <label for="name">Product Name</label>
                            <input type="text" name="name" id="name">
                        </div>

                        <div>
                            <label for="price">Price(Unit)</label>
                            <input type="number" name="price" id="price" min="1" step="any">
                        </div>

                        <div>
                            <label for="expiry">Expires on</label>
                            <input type="date" name="expiry" id="expiry">
                        </div>

                        <div>
                            <label for="description">Description</label>
                            <textarea name="description" id="description" cols="30" rows="10"></textarea>
                        </div>

                        <div class="activate">
                            <button type="submit" class="btn-1a">Save product</button>
                        </div>
                    </form>
                </div>
                <aside class="admin-menu">
                    <p>Connected as, <?= strip_tags($_SESSION['admin_session']) ?></p>
                    <ul>
                        <li><a href="dashboard.php">Dashboard</a></li>
                        <li><a href="add-admin.php">Add Admin</a></li>
                        <li><a href="add-product.php">Add Product</a></li>
                        <li><a href="list-products.php">List Products</a></li>
                        <li><a href="logout.php">Logout</a></li>
                    </ul>
                </aside>

                <div style="clear:both"> </div>
            </div>

            <footer>
                <?= date("Y") ?> &copy; lancecourse.com - Project by <a href="http://zooboole.me" target="_blank">zooboole</a> - Credit to <a href="http://tympanus.net/codrops/2013/06/13/creative-button-styles/" target="_blank">tympanus.net</a>
            </footer>
        </main>
    </body>
</html>

process-new-product.php

<?php

    /*
     * We process the admin login form here
     */

    // Start from getting the hader which contains some settings we need
    require_once 'includes/header.php';

    // require the admins class which containes most functions applied to admins
    require_once ROOT."../includes/classes/admin-class.php";

    $admins     = new Admins($dbh);

    // check if the form is submitted

    if (isset($_POST)) 
    {
        // If the form is submitted

        // first we check if all required fields are filled out
        // In this case the productname, price and the expiry date
        $errors = array();

        foreach($_POST as $key => $value) 
        {
          if((empty($value) || trim($value) == '') && $key!='description') {
            $errors[$key] = "The field ".$key." should not be empty.";
          }
          $$key =  $value;
        }

        // Description is not set in the loop
        $description = $_POST['description'];

        // If there is any error we send back to the form
        if (!empty($errors) || sizeof($errors) != 0) 
        {
            session::set('errors', $errors);
            $commons->redirectTo(SITE_PATH.'add-product.php');
        }

        // We've checked everything, 
        // now we can CREATE the admin in the admins table

        if (!$admins->addNewProduct($name, $price, $expiry, $description)) 
        {

            session::set('errors', ['An error occured while saving the new product.']);
            $commons->redirectTo(SITE_PATH.'add-product.php');

        }

        // Else we display a confirmation message
        session::set('confirm', 'New product added successfully!');
        $commons->redirectTo(SITE_PATH.'add-product.php');

    }

Finally the source code for includes/classes/admin-class.php

<?php

    /**
    * The admins class
    * It contains all action and behaviours admins may have
    */
    class Admins
    {

        private $dbh = null;

        public function __construct($db)
        {
            $this->dbh = $db->dbh;
        }

        public function loginAdmin($username, $password)
        {
            //Un-comment this to see a cryptogram of a password 
            // echo session::hashPassword($password);
            // die;
            $request = $this->dbh->prepare("SELECT username, password FROM admins WHERE username = ?");
            if($request->execute( array($username) ))
            {
                // This is an array of objects.
                // Remember we setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_OBJ); in config/dbconnection.php
                $data = $request->fetchAll();

                // But if things are right, the array should contain only one object, the corresponding user
                // so, we can do this
                $data = $data[0];

                return session::passwordMatch($password, $data->password) ? true : false;

            }else{
                return false;
            }

        }

        /**
         * Check if the admin username is unique
         * If though we've set this criteria in our database,
         * It's good to make sure the user is not try that
         * @param   $username The username
         * @return Boolean If the username is already usedor not
         * 
         */
        public function adminExists( $username )
        {
            $request = $this->dbh->prepare("SELECT username FROM admins WHERE username = ?");
            $request->execute([$username]);
            $Admindata = $request->fetchAll();
            return sizeof($Admindata) != 0;
        }

        /**
         * Compare two passwords
         * @param String $password1, $password2 The two passwords
         * @return  Boolean Either true or false
         */

        public function ArePasswordsSame( $password1, $password2 )
        {
            return strcmp( $password1, $password2 ) == 0;
        }

        /**
         * Create a new row of admin
         * @param String $username New admin username
         * @param String $password New Admin password
         * @return Boolean The final state of the action
         * 
         */

        public function addNewAdmin($username, $password)
        {
            $request = $this->dbh->prepare("INSERT INTO admins (username, password) VALUES(?,?) ");

            // Do not forget to encrypt the pasword before saving
            return $request->execute([$username, session::hashPassword($password)]);
        }

        /**
         * Create a new row of product
         * 
         */
        public function addNewProduct($name, $price, $expiry, $description)
        {
            $request = $this->dbh->prepare("INSERT INTO products (product_name, product_price, product_expires_on, product_description, created_on) VALUES(?,?,?,?,?) ");

            // Do not forget to encrypt the pasword before saving
            return $request->execute([$name, $price, $expiry, $description, time()]);
        }

    }

Bottom line

That's it. In the next part we'll end the project with the possibility of listing products(READ), editing(UPDATE), and deleting(DELETE) them. And I will also be uploading my source code for you. Meanwhile the demo is here, and use admin as username and password.

Thanks for following. Don't forget to share this with friends.

Last updated 2024-01-11 UTC